Backend done?
This commit is contained in:
Binary file not shown.
@@ -1,89 +0,0 @@
|
|||||||
// contentScript.js
|
|
||||||
|
|
||||||
const styleElement = document.createElement('style');
|
|
||||||
// language=CSS
|
|
||||||
styleElement.textContent = `
|
|
||||||
.ff-addon-title {
|
|
||||||
margin: 0;
|
|
||||||
font-weight: 600;
|
|
||||||
line-height: 30px;
|
|
||||||
font-size: 18px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.ff-addon-title-container {
|
|
||||||
margin-bottom: 12px;
|
|
||||||
width: 100%;
|
|
||||||
}
|
|
||||||
|
|
||||||
.ff-addon-hr {
|
|
||||||
margin: 0px 0px 16px;
|
|
||||||
border-width: 0px 0px thin;
|
|
||||||
border-style: solid;
|
|
||||||
border-color: rgb(54, 58, 61);
|
|
||||||
}
|
|
||||||
|
|
||||||
.ff-addon-container {
|
|
||||||
margin-bottom: 18px;
|
|
||||||
}`;
|
|
||||||
document.head.appendChild(styleElement);
|
|
||||||
|
|
||||||
const scriptElement = document.createElement('script');
|
|
||||||
// language=JavaScript
|
|
||||||
scriptElement.textContent = `
|
|
||||||
async function doJsonFetch(token, method, url) {
|
|
||||||
const res = await fetch(url,
|
|
||||||
{
|
|
||||||
method: method,
|
|
||||||
credentials: 'same-origin',
|
|
||||||
headers: {
|
|
||||||
"Authorization": "Bearer "+token
|
|
||||||
}
|
|
||||||
})
|
|
||||||
return await res.json()
|
|
||||||
}
|
|
||||||
|
|
||||||
async function onButtonClick() {
|
|
||||||
const loginToken = localStorage.getItem('LOGIN_TOKEN');
|
|
||||||
const jsonToken = loginToken && JSON.parse(loginToken);
|
|
||||||
if (!jsonToken?.access_token) {
|
|
||||||
console.error("No access token found!", jsonToken)
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
const householdBooks = await doJsonFetch(jsonToken?.access_token, "GET", "https://rentablo.de/api/v1/accounts/selectGroups/householdBook?fallbackAccountType[]=02_cash&excludeManuallyMaintainedFallbackAccounts=true")
|
|
||||||
console.log(householdBooks)
|
|
||||||
const accountIds = householdBooks.accountIds
|
|
||||||
const accountIdsQuery = "accountId[]="+accountIds.join("&accountId[]=")
|
|
||||||
const transactions = await doJsonFetch(jsonToken?.access_token, "GET", "https://rentablo.de/api/v1/transactions?"+accountIdsQuery+"&includeAdjustingEntries=false&skipManuallyCreatedTransactions=true&minDate=2024-01-01&maxDate=2024-01-31&order=date+desc&perPage=5000")
|
|
||||||
console.log(transactions)
|
|
||||||
}
|
|
||||||
`;
|
|
||||||
document.head.appendChild(scriptElement);
|
|
||||||
|
|
||||||
let parent
|
|
||||||
const paragraphs = document.getElementsByTagName('p');
|
|
||||||
for (let i = 0; i < paragraphs.length; i++) {
|
|
||||||
if (paragraphs[i].textContent.includes('Transaktionen')) {
|
|
||||||
parent = paragraphs[i].parentNode.parentNode;
|
|
||||||
break; // Stop searching once found
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
const configDiv = document.getElementById("configDiv") || document.createElement("div")
|
|
||||||
configDiv.remove()
|
|
||||||
// language=HTML
|
|
||||||
configDiv.innerHTML = `
|
|
||||||
<div class='MuiBox-root ff-addon-title-container'>
|
|
||||||
<p class="MuiTypography-root MuiTypography-subtitle1 ff-addon-title">Konfiguriere Deine Zuordnungen</p>
|
|
||||||
</div>
|
|
||||||
<hr class="MuiDivider-root MuiDivider-fullWidth ff-addon-hr"/>
|
|
||||||
<div>
|
|
||||||
<button id="ff-addon-submit" onclick="onButtonClick()">
|
|
||||||
Get all
|
|
||||||
</button>
|
|
||||||
</div>
|
|
||||||
`
|
|
||||||
configDiv.id = "configDiv"
|
|
||||||
configDiv.className = "MuiBox-root ff-addon-container"
|
|
||||||
|
|
||||||
parent.parentNode.insertBefore(configDiv, parent)
|
|
||||||
|
|
||||||
104
src/head.js
Normal file
104
src/head.js
Normal file
@@ -0,0 +1,104 @@
|
|||||||
|
async function doJsonFetch(token, method, url) {
|
||||||
|
const res = await fetch(url,
|
||||||
|
{
|
||||||
|
method: method,
|
||||||
|
credentials: 'same-origin',
|
||||||
|
headers: {
|
||||||
|
"Authorization": "Bearer "+token
|
||||||
|
}
|
||||||
|
})
|
||||||
|
return await res.json()
|
||||||
|
}
|
||||||
|
|
||||||
|
function getLoginToken() {
|
||||||
|
const loginToken = localStorage.getItem('LOGIN_TOKEN');
|
||||||
|
const jsonToken = loginToken && JSON.parse(loginToken);
|
||||||
|
const accessToken = jsonToken?.access_token
|
||||||
|
if (!accessToken) onsole.error("No access token available!")
|
||||||
|
return accessToken
|
||||||
|
}
|
||||||
|
|
||||||
|
async function onButtonClick() {
|
||||||
|
const accessToken = getLoginToken()
|
||||||
|
if (!accessToken) return;
|
||||||
|
|
||||||
|
const householdBooks = await doJsonFetch(accessToken, "GET", "https://rentablo.de/api/v1/accounts/selectGroups/householdBook?fallbackAccountType[]=02_cash&excludeManuallyMaintainedFallbackAccounts=true")
|
||||||
|
console.log(householdBooks)
|
||||||
|
const accountIds = householdBooks.accountIds
|
||||||
|
const accountIdsQuery = "accountId[]="+accountIds.join("&accountId[]=")
|
||||||
|
const transactions = await doJsonFetch(accessToken, "GET", "https://rentablo.de/api/v1/transactions?"+accountIdsQuery+"&includeAdjustingEntries=false&skipManuallyCreatedTransactions=true&minDate=2024-01-01&maxDate=2024-01-31&order=date+desc&perPage=5000")
|
||||||
|
console.log(transactions)
|
||||||
|
}
|
||||||
|
|
||||||
|
async function onInit() {
|
||||||
|
const accessToken = getLoginToken()
|
||||||
|
if (!accessToken) return;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Represents the structure of the JSON data for categories.
|
||||||
|
*
|
||||||
|
* @typedef {Object} Category
|
||||||
|
* @property {number} id - The unique identifier for the category.
|
||||||
|
* @property {string} name - The name of the category.
|
||||||
|
* @property {number|null} parentId - The identifier of the parent category, or null if it's a top-level category.
|
||||||
|
* @property {boolean} isCustom - Indicates whether the category is custom.
|
||||||
|
* @property {number[]} children - An array of child categories.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @type {Category[]}
|
||||||
|
*/
|
||||||
|
const categories = (await doJsonFetch(accessToken, "GET", "https://rentablo.de/api/v1/categories")).categories
|
||||||
|
console.log(categories)
|
||||||
|
const nodes = {}
|
||||||
|
const roots = []
|
||||||
|
for (const category of categories) {
|
||||||
|
nodes[category.id] = {
|
||||||
|
id: category.id,
|
||||||
|
name: category.name,
|
||||||
|
children: category.children
|
||||||
|
}
|
||||||
|
if (typeof category.parentId !== "number") roots.push(category.id)
|
||||||
|
}
|
||||||
|
|
||||||
|
console.log(nodes)
|
||||||
|
console.log(roots)
|
||||||
|
|
||||||
|
function replaceChildrenIds(ids) {
|
||||||
|
return ids.map(id => {
|
||||||
|
const node = nodes[id]
|
||||||
|
node.children = replaceChildrenIds(node.children)
|
||||||
|
return node
|
||||||
|
})
|
||||||
|
}
|
||||||
|
const newRoots = replaceChildrenIds(roots)
|
||||||
|
console.log(newRoots)
|
||||||
|
|
||||||
|
const tableContainer = document.getElementsByClassName("ff-addon-table-container").item(0)
|
||||||
|
// language=HTML
|
||||||
|
tableContainer.innerHTML = `
|
||||||
|
<div id="ff-addon-table">
|
||||||
|
<div>Participant</div>
|
||||||
|
<div>Subject</div>
|
||||||
|
<div>Min. Volume</div>
|
||||||
|
<div>Max. Volume</div>
|
||||||
|
<div>Categories</div>
|
||||||
|
|
||||||
|
<input type="text" class="participant" />
|
||||||
|
<input type="text" class="subject" />
|
||||||
|
<input type="number" class="min-volume" />
|
||||||
|
<input type="number" class="max-volume" />
|
||||||
|
<select class="categories">
|
||||||
|
<option value="Category 1">Category 1</option>
|
||||||
|
<option value="Category 2">Category 2</option>
|
||||||
|
<option value="Category 3">Category 3</option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<button id="submit-button" onclick="onButtonClick()">Submit</button>
|
||||||
|
`
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
onInit().catch(console.error)
|
||||||
@@ -6,7 +6,7 @@
|
|||||||
"content_scripts": [
|
"content_scripts": [
|
||||||
{
|
{
|
||||||
"matches": ["<all_urls>"],
|
"matches": ["<all_urls>"],
|
||||||
"js": ["contentScript.js"]
|
"js": ["setup.js", "head.js"]
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
50
src/setup.js
Normal file
50
src/setup.js
Normal file
@@ -0,0 +1,50 @@
|
|||||||
|
const styleElement = document.createElement('style');
|
||||||
|
// language=CSS
|
||||||
|
styleElement.textContent = `
|
||||||
|
.ff-addon-title {
|
||||||
|
margin: 0;
|
||||||
|
font-weight: 600;
|
||||||
|
line-height: 30px;
|
||||||
|
font-size: 18px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.ff-addon-title-container {
|
||||||
|
margin-bottom: 12px;
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.ff-addon-hr {
|
||||||
|
margin: 0px 0px 16px;
|
||||||
|
border-width: 0px 0px thin;
|
||||||
|
border-style: solid;
|
||||||
|
border-color: rgb(54, 58, 61);
|
||||||
|
}
|
||||||
|
|
||||||
|
.ff-addon-container {
|
||||||
|
margin-bottom: 18px;
|
||||||
|
}`;
|
||||||
|
document.head.appendChild(styleElement);
|
||||||
|
|
||||||
|
let parent
|
||||||
|
const paragraphs = document.getElementsByTagName('p');
|
||||||
|
for (let i = 0; i < paragraphs.length; i++) {
|
||||||
|
if (paragraphs[i].textContent.includes('Transaktionen')) {
|
||||||
|
parent = paragraphs[i].parentNode.parentNode;
|
||||||
|
break; // Stop searching once found
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const configDiv = document.getElementById("configDiv") || document.createElement("div")
|
||||||
|
configDiv.remove()
|
||||||
|
// language=HTML
|
||||||
|
configDiv.innerHTML = `
|
||||||
|
<div class='MuiBox-root ff-addon-title-container'>
|
||||||
|
<p class="MuiTypography-root MuiTypography-subtitle1 ff-addon-title">Konfiguriere Deine Zuordnungen</p>
|
||||||
|
</div>
|
||||||
|
<hr class="MuiDivider-root MuiDivider-fullWidth ff-addon-hr"/>
|
||||||
|
<div class='MuiBox-root ff-addon-table-container'></div>
|
||||||
|
`
|
||||||
|
configDiv.id = "configDiv"
|
||||||
|
configDiv.className = "MuiBox-root ff-addon-container"
|
||||||
|
|
||||||
|
parent.parentNode.insertBefore(configDiv, parent)
|
||||||
Reference in New Issue
Block a user