Is MutationObserver called for each DOM node insert or is the call batched?

I am trying to delete some scripts on page load via the use of TamperMonkey.

I am using MutationObserver to figure out when a script event loads and if so delete it and place my script on it.

// ==UserScript==
// @name         Block Scripts Before Execution
// @namespace    http://tampermonkey.net/
// @version      0.1
// @description  Run a script before any other scripts on the page
// @author       You
// @match        *://*/*
// @grant        none
// @run-at       document-start
// ==/UserScript==

(function() {
    'use strict';

    // Use MutationObserver to watch for script elements being added to the DOM
    const observer = new MutationObserver((mutationsList, observer) => {
        for (let mutation of mutationsList) {
            if (mutation.type === 'childList') {
                for (let node of mutation.addedNodes) {
                    if (node.tagName === 'SCRIPT') {
                        console.log('Blocked script:', node.src || 'inline script');
                        node.remove(); // Block the script by removing it
                    }
                }
            }
        }
    });

    // Start observing the DOM for new script tags
    observer.observe(document.head, {
        childList: true,
        subtree: true
    });

})();

Now my question is that will the callback be called for each and every DOM node insertion ?

Or will it be batched and then called ?

Because it is imperative that I replace the script before the window.DOMContentLoaded is fired.

Check if excel sheet is protected or not when using WorkbookReader in exceljs

I am working on read excel file by using exceljs. I have limitation where I can use this package only and no any other third party packages. Since, I need to handle with big excel file also I need to use WorkbookReader. But issue is I don’t know the way or if have any way to check if sheet is protected or not.

import * as ExcelJS from 'exceljs';

const workbookReader = new ExcelJS.stream.xlsx.WorkbookReader(
        filePath,
        {},
      );
      let isFirstSheetCompleted = false;
      const readResponseData = [];
      for await (const worksheetReader of workbookReader) {
        if (!isFirstSheetCompleted ) {
          //Need to check if sheet is protected or not
          for await (const row of worksheetReader) {
            const rowData = (row.values as any).slice(1);
            readResponseData.push(rowData);
          }
        }
        isFirstSheetCompleted = true;
      }

I just attached the working code. In the comment section I need to check if sheet is protected or not.

Just for information. I tried also (worksheetReader as any).sheetProtection that return undefined and not worked, assuming that was worked when used new Workbook()

VSCode paste handlers taking tooooo long with no result

In a new day I open VSCode and trying to copy a code and when pasting it shows an annoying loader with long time and no result and when i hover it says:
Running paste handlers. Click to cancel and do basic paste.
and i need to click to do basic paste, why the paste handlers to too much time with no result. pls help, this problem persist for me for days….

I tried to disable all the extensions and i already disabling auto format code and the same problem.

I’m expecting to paste the code but no result……..

How to correct this flow in latest Angular?

I have been working on this using latest Angular signals and rxResource, but came to this issue

  // this will make API call for chain everytime lastLoadedscript is set
  myResource = rxResource<{ [key: string]: strategy[] }, { seg: number, sid: number }>({
    request: () => {
      let script = this.stateService.lastLoadedScript()
      let tempReq = {
        seg: script.id || 0,
        sid: script.sid
      }
      return tempReq
    },
    loader: ({ request }) => {
      return this.myService.getExplist(request).pipe(
        switchMap((expiryDetails: ExpiryDetails[]) => {
          this.expiryList = expiryDetails;
          this.expirySortname = this.expiryList.map(e => e.sortname);
          let script = this.stateService.lastLoadedScript();
          let tempObj = {
            "StrategyName": "*",
            "Symbol": script.name,
            "ExpiryJulian": this.expiryList[this.prebuiltExpiry()].expiry
          };
          return this.myService.getstrategy(tempObj).pipe(
            map(resp => {
              if (resp['status'] != 'success') {
                throw new Error('Invalid resp');
              }
              return processData(resp['data'])
            })
          );
        })
      );
    }
  })```


Issue here is that expList is getting each time, I need getstrategy for different expiry
goal is

  1. On page load call explist once it’s response came call getStrategy
  2. Do all subsequent call of getstrategy with simple myResource.reload() with selected expiry but dont make expiry api call.
  3. When lastLoadedScript changes repeat step 1. i.e: call exp then call get strategy

I tried seperate resource for exp but it won’t work as getStrat must be call only after explist is available

Merging linked list leetcode solution

So I was doing leetcode, in particular this question

For this, I wrote this solution

/**
 * Definition for singly-linked list.
 * function ListNode(val, next) {
 *     this.val = (val===undefined ? 0 : val)
 *     this.next = (next===undefined ? null : next)
 * }
 */
/**
 * @param {ListNode} list1
 * @param {ListNode} list2
 * @return {ListNode}
 */


var mergeLists = function(list1, list2, newList = new ListNode()) {
    if (!list1 && !list2) return newList
    if (!list1 && list2) {
        newList.next = list2
        return newList
    } 
    if (!list2 && list1) {
        newList.next = list1
        return newList
    }
    if (list1.val >= list2.val) {
        newList.next = list1
        return mergeLists(list1.next, list2, newList.next)
    } 
    if (list2.val > list1.val) {
        newList.next = list2
        return mergeLists(list1, list2.next, newList.next)
    }
};

 var mergeTwoLists = function(list1, list2) {
    const lists =  mergeLists(list1, list2)
    return lists?.next
 }

but this doesn’t work. I know this isn’t ideal solution, but I am trying to figure out what’s wrong with this code.

How to dynamically set –max-heap-size and –max-old-space-size in Node.js based on available memory?

I have a Node.js web server built with Express.js, and I’m trying to optimize memory usage and the V8 garbage collector. My understanding is that increasing the heap size allows more memory to be allocated before triggering garbage collection (GC), which can improve performance in some cases.

To achieve this, I wrote a Bash script to dynamically configure --max-heap-size and --max-old-space-size based on the available memory in the Docker container. Here is the script:

/start-node.sh

#!/bin/sh

# memory limint on Docker container
MEMORY_LIMIT=$(cat /sys/fs/cgroup/memory/memory.limit_in_bytes)

# memory limint in MB
MEMORY_LIMIT_MB=$((MEMORY_LIMIT / 1024 / 1024))

# if memory limint is too bigger (9223372036854771712 is no limit), set to 2 GB
if [ "$MEMORY_LIMIT" -gt 9223372036854771712 ]; then
  MEMORY_LIMIT_MB=2048
fi

# heap is 75% of total
HEAP_SIZE_MB=$((MEMORY_LIMIT_MB * 75 / 100))

# Old Generation is 60-80% of heap
OLD_SPACE_SIZE_MB=$((HEAP_SIZE_MB * 70 / 100))

echo "Memory limit: ${MEMORY_LIMIT_MB} MB"
echo "Setting max heap size to: ${HEAP_SIZE_MB} MB"
echo "Setting max old space size to: ${OLD_SPACE_SIZE_MB} MB"

node --max-heap-size=$((HEAP_SIZE_MB * 1024)) --max-old-space-size=${OLD_SPACE_SIZE_MB} ./server.js

My Questions:

  1. Is this approach correct for dynamically configuring memory in Node.js within a Docker environment?
  2. Are there any improvements or best practices I should consider for managing --max-heap-size and --max-old-space-size?
  3. Is it safe to assume that allocating 75% of the total memory to the heap and 70% of the heap to the old generation is a good rule of thumb?

Why are my draggable elements not functioning as expected?

I’m trying to make multiple elements draggable using interact.js in my CodePen project, but it’s not working as expected. When I add the draggable=”true” attribute to the elements, not all of them respond correctly to drag events, only the last one. All elements before the last one have a strange behaviour: At start drag, drag end is already fired.

<div class="configurator-container">
    <div class="elements-panel">
        <div class="element" id="element-1" draggable="true">
            Element 1
        </div>
        <div class="element" id="element-2" draggable="true">
            Element 2
        </div>
        <div class="element" id="element-3" draggable="true">
            Element 3
        </div>
        <div class="element" id="element-4" draggable="true">
            Element 4
        </div>
        <!-- Add more elements as needed -->
    </div>

    <div class="board-container">
        <div class="board" id="board">
            <!-- Dynamically add elements here -->
        </div>
    </div>
</div>

Here’s my setup:

  • I’m using interact.js to handle the dragging behavior.
  • I need each element to be draggable and constrained within the parent container.

Here’s my CodePen: https://codepen.io/brentrug/pen/OPLEJKj

What I’ve tried:

  • The draggable attribute is applied to each element.
  • I applied the inertia, autoScroll, and restrict modifiers to make the dragging smooth and restrict movement to the parent container.

What I expect:

  • Each element should be dragable correctly. Not only the last one

Can anyone help me figure out why this isn’t working?

Any guidance on how I can fix this would be greatly appreciated!

This is the JS code:

// Select all the .element divs
const elements = document.querySelectorAll('.element');

// Loop through each element and apply interact separately
elements.forEach(element => {
    interact(element)
        .draggable({
            inertia: false, // Remove inertia for more responsive dragging
            autoScroll: false,
            modifiers: [
                interact.modifiers.restrict({
                    restriction: 'parent',
                    endOnly: true
                })
            ],
            listeners: {
                start(event) {
        console.log('Drag started on', event.target.id);
                    const { target } = event;
                    target.classList.add('dragging');
                    target.style.zIndex = '1000'; // Higher z-index to ensure it's above other elements

                    // Set initial position for 'absolute' positioning (only for the dragged element)
                    const rect = target.getBoundingClientRect();
                    target.setAttribute('data-x', rect.left);
                    target.setAttribute('data-y', rect.top);

                    // Ensure position is set to absolute for the dragged element
                    target.style.position = 'absolute';
                },
                move(event) {
        console.log('Dragging', event.target.id);
                    const { target } = event;

                    // Calculate new left and top values
                    const x = (parseFloat(target.getAttribute('data-x')) || 0) + event.dx;
                    const y = (parseFloat(target.getAttribute('data-y')) || 0) + event.dy;

                    // Set the left and top properties for movement
                    target.style.left = `${x}px`;
                    target.style.top = `${y}px`;

                    // Store the new position
                    target.setAttribute('data-x', x);
                    target.setAttribute('data-y', y);
                },
                end(event) {
        console.log('Drag ended on', event.target.id);
                    const { target } = event;

                    // Reset the element's position after drop
                    target.style.position = ''; // Reset position to original state
                    target.style.left = '';
                    target.style.top = '';
                    target.removeAttribute('data-x');
                    target.removeAttribute('data-y');
                    target.classList.remove('dragging');
                    target.style.zIndex = '1';

                    // Get the board where the element was dropped
                    const board = document.querySelector('.board'); // Assuming this is your board element

                    // Calculate final position relative to the board
                    const dragRect = event.rect;
                    const boardRect = board.getBoundingClientRect();
                    const x = dragRect.left - boardRect.left;
                    const y = dragRect.top - boardRect.top;

                    // Account for scroll position
                    const scrollX = window.scrollX || window.pageXOffset;
                    const scrollY = window.scrollY || window.pageYOffset;

                    // Adjust coordinates for scroll position
                    const adjustedX = x - scrollX;
                    const adjustedY = y - scrollY;

                    // Create new element with adjusted coordinates
                    const newElement = createElementOnBoard(target, adjustedX, adjustedY);
                    board.appendChild(newElement); // Append the new element to the board
                }
            }
        });
});

How to remove the gap between 2 events with the same/overlapping time slot in timeGridView?

Currently I am having trouble trying to remove the gap between 2 events that have occupy the same timeslot or have overlapping timeslot in FullCalendar’s timeGridView like in the image. Note that I cannot change the size of the event cards because of the requirement is that they must be fixed to 1/4 of the row.

Current view

I have tried using the eventOverlap option in the calendar object. I have tried change some of the css here and there but still have no clue what is causing the gap. I have looked through the documentation and did some googling to no avail.

This is my current code for my FullCalendar render:

document.addEventListener('DOMContentLoaded', function () {
    const calendarEl = document.getElementById('event-agenda');

    if (!calendarEl || !eventDays.length || !eventDays[0].date_start) {
        return;
    }

    const calendar = new FullCalendar.Calendar(calendarEl, {
        initialView: 'timeGridDay',
        initialDate: eventDays[0].date_start,
        headerToolbar: false,
        dayHeaders: false,
        allDaySlot: false,
        slotMinTime: timeRangeOfEventDays[eventDays[0].date_start]?.slotMinTime ?? '10:00:00',
        slotMaxTime: timeRangeOfEventDays[eventDays[0].date_start]?.slotMaxTime ?? '24:01:00', // Include midnight
        slotDuration: '01:00:00',
        slotLabelFormat: {
            hour: 'numeric',
            minute: '2-digit',
            omitZeroMinute: true,
        },
        slotEventOverlap: false,
        contentHeight: 'auto',
        events: eventActivities,
        eventDidMount: function(info) {
            const eventDesc = info.event._def.extendedProps.description
            tippy(info.el, {
                content: `
                    <p>${info.event._def.title}</p>
                    ${
                        eventDesc ? `<br><p>About event: ${eventDesc}</p>` : ''
                    }
                `,
                placement: 'top',
                allowHTML: true,
            });
        },
        eventClick: function (info) {
            info.jsEvent.preventDefault();
            return;
        },
        eventContent: function (info) {
            const duration = (new Date(info.event.end) - new Date(info.event.start)) / (60 * 1000); // Duration in minutes
            const isShortEvent = duration < 30;
            const isMediumEvent = duration < 60;
            const isHourLongEvent = duration === 60;
            const isLongEvent = duration <= 90;
            const isExtraLongEvent = duration > 90;

            if (isShortEvent) {
                return {
                    html: `
                        <div class="event-agenda-small-item">
                            <span class="event-agenda-small-item-time">
                                ${getTimeInAMPMFormat(info.event.start)} - ${getTimeInAMPMFormat(info.event.end)}
                            </span>
                            <span class="event-agenda-small-item-title">${info.event.title}</span>
                            ${ info.event.url ? `<img src="/storage/${info.event.url}">` : ''}
                        </div>
                    `
                }
            } else {

                let descClass = '';
                if (isHourLongEvent) {
                    descClass = 'event-item-hour-long-desc';
                }
                else if (isLongEvent) {
                    descClass = 'event-item-long-desc';
                }
                else if (isExtraLongEvent) {
                    descClass = 'event-item-extra-long-desc';
                }

                const container = document.createElement('div');
                container.innerHTML = info.event.extendedProps.description ?? "";

                const parsedElement = container.firstChild;

                if (parsedElement) {
                    parsedElement.classList.add(descClass);
                }

                return {
                    html: `
                        <div class="event-agenda-item">
                            <div class="event-agenda-item-top">
                                <div class="event-agenda-item-info">
                                    <div class="event-agenda-item-time">
                                        ${getTimeInAMPMFormat(info.event.start)} - ${getTimeInAMPMFormat(info.event.end)}
                                    </div>
                                   <div class="${isMediumEvent ? 'event-agenda-medium-title' : 'event-agenda-item-title'}">${info.event.title}</div>
                                </div>
                                ${info.event.url ? `<img src="/storage/${info.event.url}">` : ''}
                            </div>
                            ${ info.event.extendedProps.description && !isMediumEvent ? `
                                <div class="event-agenda-item-bottom">
                                    ${parsedElement.outerHTML}
                                </div>` : ''
                            }
                        </div>
                    `
                }
            }
        }
    });

    calendar.render();
}

How to Detect Brightness Up/Down Keys?

Question:

I’m working on an Electron application with a React frontend and attempting to listen for the brightness up and brightness down keys on a Linux Ubuntu environment. These keys have the following key codes:

  • Brightness Up: 269025026
  • Brightness Down: 269025027

What I’ve Tried:

  1. Keydown Event Listener in React:
    I added a keydown event listener, and it works for most keys, but it doesn’t trigger for the brightness keys.

  2. Mousetrap with Custom Keycodes:
    I tried adding the custom keycodes for these keys:

    Mousetrap.addKeycodes({
        269025026: "brightness_up",
    });
    

    Unfortunately, this didn’t work either.

  3. Electron Main Process with globalShortcut.register:
    I looked for the relevant key codes in the Electron Accelerator documentation, but I couldn’t find support for the brightness keys.

  4. Using Mousetrap in Electron Main:
    I attempted to use Mousetrap in the Electron main process, but it threw the following error:

    (node:980858) UnhandledPromiseRejectionWarning: TypeError: Mousetrap.addKeycodes is not a function
    at createWindow (file:///home/casillas/amitai/Casillas/casillas-frontend/dist-electron/main.js:2457:13)
    

    I also received an unhandled promise rejection warning.

Additional Information:

Interestingly, I was able to detect the brightness keys using Python’s pynput library with keyboard.Listener.

My Goal:

I want to detect these brightness keys and eventually control the screen brightness directly from my Electron application.

Question:

  • Why might the brightness keys not be triggering in the browser window of my Electron app?
  • Is there a way to detect these keys reliably in Electron, either in the renderer or main process?
  • Are there alternative approaches or libraries to achieve this functionality?

Any help or suggestions would be greatly appreciated!

Vite build produces a bundle with an absolute system path

I am converting a project from webpack to vite and most things work fine, dev-server is good and the build succeeds.

However the final bundle contains an import to one package that is an absolute path on my system to the node_modules dir. This package is not imported by my project but by a dependecy of mine.

To be specific it is json-schema-merge-allof which is a dependency of @rjsf/utils.

It is the only such issue in a 5MB bundle with hundreds of other dependencies.

Here is the vite config file. I tried a variety of options, like setting package to be external (which makes the final bundle contain import g8e from"json-schema-merge-allof which is still not valid) using commonjs plugin, setting optimize deps for rjsf.

import { defineConfig } from 'vite';
import react from '@vitejs/plugin-react';
import path from 'path';
import commonjs from 'vite-plugin-commonjs';

export default defineConfig({
  root: path.resolve(__dirname, 'src/frontend'),
  envDir: '../../',
  build: {
    chunkSizeWarningLimit: 10000,
    rollupOptions: {
      input: {
        main: path.resolve(__dirname, 'src/frontend/index.html'),
        loading: path.resolve(__dirname, 'src/frontend/indexDownloader.ts'),
        login: path.resolve(__dirname, 'src/frontend/login.html'),
      },
      
      external: ['../common', '../types', '../generated'],
      output: {
        entryFileNames: '[name]-bundle.js',
      },
    },
    outDir: path.resolve(__dirname, 'dist/static'),
    emptyOutDir: true,
  },
  server: {
    open: '/',
    port: 8082,
  },
  resolve: {
    alias: {
        '@common': path.resolve(__dirname, 'src/common'),
        '@generated': path.resolve(__dirname, 'src/generated'),
        '@types': path.resolve(__dirname, 'src/types'),
    },
    extensions: ['.tsx', '.ts', '.js', '.d.ts'],
  },
  plugins: [
    react(),
    commonjs(),
  ],
  css: {
    preprocessorOptions: {
      scss: {},
    },
  },
  optimizeDeps: {
    include: ['@generated/radarimage'], // Pre-bundle the module
  },
});

Next.js “jsxImportSource”: “@emotion/react”

Adding “jsxImportSource”: “@emotion/react” to tsconfig results in error.

import { Provider } from "@/app/provider";

export default function Layout({ children }: { children: React.ReactNode }) {
  return (
    <html lang="en">
      <body>
        <Provider>
          {children}
        </Provider>
      </body>
    </html>
  );
}

“jsxImportSource”: “@emotion/react”
if I add this and specify “use client”, the error is resolved. I’m curious as to why.

“jsxImportSource”: “@emotion/react”
I would like to know what role this plays and why an error occurs if I add it.

For reference, the error is

TypeError: createContext only works in Client Components. Add the “use
client” directive at the top of the file to use it.

Leaflet Search Control on JavaScript

I am trying to make a web visor. Everything is ok until I try to enter a search control bar in my website. I use Leaflet and I was looking for some plugins to do that on its official website.

Can anyone help?

<link rel="stylesheet" href="leaflet-search-master/src/leaflet-search.css">
<script src="leaflet-search-master/src/leaflet-search.js"></script>
var controlSearch = new L.Control.Search({
  position:'topright',      
  layer: capt,
  initial: false,
  zoom: 12,
  marker: false
});

map.addControl( controlSearch );

Unable to load environment variable in vite.config.js

I am working on a Vite project where I need to load an environment variable (APP_PORT) from a .env file in my vite.config.js. However, it seems that the variable is not being loaded correctly, and my fallback value (5000) is being used instead.
Project structure:.

project/
├── .env
├── frontend/
│   ├── vite.config.js
│   └── ...

The .env file is located in the root directory of the project.
The vite.config.js file is inside the frontend folder.
.env file

APP_PORT=5001

vite.config.js file

import { defineConfig, loadEnv } from 'vite';
import react from '@vitejs/plugin-react';
import path from 'path';
import { fileURLToPath } from 'url';

const __dirname = path.dirname(fileURLToPath(import.meta.url));

export default ({ mode }) => {
  // Load environment variables for the current mode
  const env = loadEnv(mode, path.resolve(__dirname, '../', ''));
  const port = env.APP_PORT;
  console.log(
    'Loaded environment variables for mode:', env,
    'Path:', __dirname,
    'Port:', port);

  return defineConfig({
    root: 'frontend',
    plugins: [react()],
    optimizeDeps: {
      exclude: ['lucide-react'],
    },
    server: {
      proxy: {
        '/api': {
          target: `http://127.0.0.1:${port || '5000'}`, // Use the loaded env variable
          changeOrigin: true,
          secure: false,
          rewrite: (path) => path.replace(/^/api/, ''),
          configure: (proxy) => {
            proxy.on('proxyReq', (proxyReq, req) => {
              console.log('Proxying request:', req.url, 'to:', proxyReq.getHeader('host'));
            });
          }
        }
      }
    }
  })
};

Even though I’ve specified APP_PORT in the .env file, it always falls back to the default value (5000). The console.log in vite.config.js shows undefined for APP_PORT.
What I have tried:
1. Verified the .env file is in the root directory and contains the correct variable (APP_PORT=5001).
2. Restarted the Vite development server after making changes to the .env file.
3. Ensured that path.resolve(__dirname, ‘../’) points to the correct directory for the .env file.
4. Added a debug log to check the loaded environment variables, but I get undefined.
Expected Behavior:
The APP_PORT variable from the .env file should be loaded, and the proxy in vite.config.js should use port 5001.
Environment:.
Node: v23.4.0
VITE: v6.0.3
OS: macOS

How can I protect my HTML, CSS, and JavaScript code from being easily viewed in the browser? [closed]

I’ve developed a basic website using plain HTML, CSS, and JavaScript and hosted it on a server. When I access the site and use Ctrl+U or the browser’s developer tools, the entire source code (HTML structure, CSS styles, and JavaScript) is easily visible and readable. This concerns me because it makes it simple for others to copy or reuse the code. but I’d like to make it harder for others to view or reuse the code. What are my options to use for hide actual source code?

I’m hosting a plain website built with HTML, CSS, and JavaScript, but when I view the source code in the browser (e.g., using Ctrl+U), the entire code is visible as-is. Are there any best practices or techniques to prevent users from accessing or copying the source code easily? I understand that complete protection isn’t possible, but I’d like to make it harder for others to view or reuse the code. What are my options?

What are the best practices or common approaches developers use in this scenario? Are there tools or methods to obfuscate the code or otherwise secure it to some extent? Any advice on how to balance usability and security would be appreciated.