Skip to content

Instantly share code, notes, and snippets.

@jaandrle
Last active August 4, 2018 11:05
Show Gist options
  • Save jaandrle/bada8c2153d58c7040b43d88b825e9dc to your computer and use it in GitHub Desktop.
Save jaandrle/bada8c2153d58c7040b43d88b825e9dc to your computer and use it in GitHub Desktop.
Trello "Export"

READ ME

This is in-browser JavaScript code which provide possibility to quick get information from Trello dashboard.

It was tested mainly on Firefox.

The Classes_GetTrelloStuff implementation is necessary pasted to browser console. The class has now two methods "toJSON" and "toMarkdown" (primary for GitHub).

The class allow to decide which cols schould be exported. In constructor use param "col_list_min" (indexing starts by 0) and "col_list_max" (the same as "col_list_min" or string like "rest" which represents rest cols).

const instance= Classes_GetTrelloStuff({col_list_min: 0, col_list_max: 0}); //exports only first col
const instance2= Classes_GetTrelloStuff({col_list_min: 0, col_list_max: "rest"}); //exports all cols (it is default set up so it is similar to Classes_GetTrelloStuff();

The Method "toJSON" returns JSON which repeting this structure:

"col_name": {
_ "task_id": {
___ "name": string,
___ "last_change": string,
___ "url": string,
___ "labels": string,
___ "description": string (in the case there is no description it contains "---"),
___ "checklists": {} or {
______   "checklist_name": {
________     "item_name": bool (if checked)
______   },...
___ },
___ "attachments": {} or {
______   "attachment_name": string (url link),
______   ...
___ },
___ "comments": {} or {
______    "comment_id": {
_______      "url": string (url link)
_______      "time": string
_______      "preview": string (max. 103 chars)
______   },...
___ },
_ },...
function Classes_GetTrelloStuff(def={}){
let {
/* Params to export only specifics cols (indexing starts by 0) */
col_list_min= 0,
col_list_max= "rest",
/* Just for better editing when somethin change on Trello */
popup_element= document.getElementsByClassName("window")[0],
col_list= document.getElementsByClassName("list-header-name-assist"),
getTasks= (actual_col)=>document.getElementsByClassName("js-list-content")[actual_col].getElementsByClassName("list-card-details"),
getCardName= (el)=>el.getElementsByClassName('js-card-name')[0],
getCardDetailTitleDOM= (popup_element)=>popup_element.getElementsByClassName('card-detail-title-assist'),
getCardDetailLastChange= (popup_element)=>popup_element.getElementsByClassName("phenom")[0].getElementsByClassName("date")[0].title,
getCardDetailIdDOM= (popup_element)=>popup_element.getElementsByClassName('plugin-card-detail-badge'),
getCardDetailLabelsDOM= (popup_element)=>popup_element.getElementsByClassName('mod-card-detail') || [],
getCardDetailDescriptionDOM= (popup_element)=>popup_element.getElementsByClassName('js-card-desc'),
getCardDetailCheckListsDOM= (popup_element)=>popup_element.getElementsByClassName('checklist'),
getCardDetailCheckListsNamesDOM= (checklist_element)=>checklist_element.getElementsByClassName("hide-on-edit")[0].textContent,
getCardDetailCheckListsElementsDOM= (checklist_element)=>checklist_element.getElementsByClassName('checklist-item'),
getCardDetailCheckListsElementsText= (check_list_item)=>check_list_item.getElementsByClassName("js-checkitem-name")[0].textContent,
getCardDetailAttachmentsDOM= (popup_element)=>popup_element.getElementsByClassName('attachment-thumbnail-name'),
getCardDetailAttachmentsLinkDOM= (popup_element)=>popup_element.getElementsByClassName('js-attachment-action'),
getCardDetailCommentsDOM= (popup_element)=>popup_element.getElementsByClassName('mod-comment-type')
}= def;
col_list_max= typeof col_list_max==="string"? col_list.length : col_list_max+1;
let actual_col= col_list_min;
let task_list= getTasks(actual_col);
let task_list_length= task_list.length;
let actual_task= 0;
let object_to_json= {};
let temp_object_task= {};
let temp_actual_col_name= "";
let text= '<!doctype html><html lang="en" dir="ltr"><head><meta charset="utf-8"><title>DHLC IN | Trello</title></head><body>';
outfunction= "JSON";
outfunctions= {
JSON: function(){console.log(JSON.stringify(object_to_json));},
Markdown: function(){
let output= "";
Object.keys(object_to_json).forEach(function(col_name,col_i){
if(col_i) output+= "\n";
output+= "## "+col_name;
Object.keys(object_to_json[col_name]).forEach(function(task_id){
const task_obj= object_to_json[col_name][task_id];
output+= "\n### "+task_obj.name;
output+= "\n**Last change:** "+task_obj.last_change+" | **ID:** ["+task_id+"]("+task_obj.url+") | **Labels:** "+task_obj.labels;
if(task_obj.description!=="---") output+= "\n#### Description\n" + task_obj.description;
output+= Object.keys(task_obj.checklists).map(function(checklist_name){
return Object.keys(task_obj.checklists[checklist_name]).reduce(function(r,item_name){
r+= "\n";
r+= task_obj.checklists[checklist_name][item_name] ? "- [x] " : "- [ ] ";
r+= item_name;
return r;
}, checklist_name);
})
.reduce((r,list) => r+"\n#### "+list,"");
if(Object.keys(task_obj.attachments).length){
output+= "\n#### Attachments" + Object.keys(task_obj.attachments).reduce(function(r,attachment_name){
return r+"\n- ["+attachment_name+"]("+task_obj.attachments[attachment_name]+")";
}, "");
}
if(Object.keys(task_obj.comments).length){
output+= "\n#### Comments Preview" + Object.keys(task_obj.comments).reduce(function(r,comment_id){
return r+"\n- "+task_obj.comments[comment_id].time+": ["+task_obj.comments[comment_id].preview+"]("+task_obj.comments[comment_id].url+")";
}, "");
}
});
});
console.log(output);
}
};
function openCol(){
actual_task= 0;
if(actual_col<col_list_max){
temp_actual_col_name= col_list[actual_col].innerText;
object_to_json[temp_actual_col_name]= {};
task_list= getTasks(actual_col++);
task_list_length= task_list.length;
openTask();
} else {
outfunctions[outfunction]();
}
}
function openTask(){
if(actual_task<task_list_length) taskParse(task_list[actual_task++]);
else openCol();
}
function taskParse(el){
const el_name= getCardName(el).textContent.trim();
wait();
function wait(){el.click();setTimeout(check, 1200);}
function check(){
if(getCardDetailTitleDOM(popup_element).length && getCardDetailIdDOM(popup_element).length){ window.requestAnimationFrame(getTexts); }
else { console.log(el_name); wait(); }
}
function getTexts(){
let temp_el;
temp_object_task= {};
console.log(popup_element.getElementsByClassName("plugin-card-detail-badge")[0].textContent.trim()+" OK");
temp_object_task.name= getCardDetailTitleDOM(popup_element)[0].innerHTML;
temp_object_task.last_change= getCardDetailLastChange(popup_element);
temp_object_task.url= location.href;
temp_object_task.labels= [].reduce.call(getCardDetailLabelsDOM(popup_element),(r,el)=>r+el.textContent+", ","");
temp_el= getCardDetailDescriptionDOM(popup_element)[0];
temp_object_task.description= temp_el && temp_el.innerText ? temp_el.innerText : "---";
temp_el= getCardDetailCheckListsDOM(popup_element);
temp_object_task.checklists= {};
[].forEach.call(temp_el, function(checklist_el,i){
let temp_list= {};
[].forEach.call(getCardDetailCheckListsElementsDOM(checklist_el), function(item,i){
temp_list[getCardDetailCheckListsElementsText(item)]= item.classList.contains("checklist-item-state-complete");
});
temp_object_task.checklists[getCardDetailCheckListsNamesDOM(checklist_el)]= temp_list;
});
temp_el= getCardDetailAttachmentsDOM(popup_element);
temp_object_task.attachments= {};
[].forEach.call(temp_el, function(item, i){
temp_object_task.attachments[item.textContent]= getCardDetailAttachmentsLinkDOM(popup_element)[i].href;
});
temp_el= getCardDetailCommentsDOM(popup_element);
temp_object_task.comments= {};
[].forEach.call(temp_el, function(item, i){
const date_el= item.getElementsByClassName("phenom-date")[0].getElementsByTagName("A")[0];
const comment_link= date_el.href;
const comment_text= item.getElementsByClassName("comment-container")[0].innerText.replace(/\n/g, " ");
temp_object_task.comments[comment_link.split("#")[1]]= {
url: comment_link,
time: date_el.title,
preview: comment_text.length > 100 ? comment_text.substr(0, 100)+"..." : comment_text
};
});
object_to_json[temp_actual_col_name][getCardDetailIdDOM(popup_element)[0].textContent.trim()]= temp_object_task;
openTask();
}
}
return Object.freeze({
toJSON: function(){outfunction= "JSON"; openCol();},
toMarkdown: function(){outfunction= "Markdown"; openCol();}
});
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment