My app works in Chrome but not iPhone; what is the difference in browsers that I am not accommodating?

I am working on a billiards scorekeeping app implemented in HTML/CSS/javascript at this repo:
https://github.com/Zenilogix-Carl/Site

I have been developing using Windows and Chrome, getting expected outputs or at least able to diagnose issues in that environment. I’ve seen it run on some friends’ iPhones and I get very different (and flawed) results. I am hoping to find someone who can help me identify and correct the issues affecting iPhone.

The three files relevant to my issue are:

  • NineBall.html
  • Billiards.js
  • styles.css

I’ve attached screenshots below. Notice that in Chrome, all balls are rendered with a drop-shadow; this is defined in the BilliardBall class and extended into BilliardBallWithState (both in Billiards.js) and, depending on current state, may be turned on or off by function updateBallState in NineBall.html. Initial state should show the drop-shadow for all balls, which it does in Chrome, but fails to on iPhone.

class BilliardBall {
    constructor(number, size, allowForShadow) {
        var colors = ["yellow", "blue", "red", "purple", "orange", "green", "brown", "var(--ballBlack)"];
        var color = Number.isInteger(number) ? colors[(number - 1) % 8] : colors[0];
        var isStripe = Number.isInteger(number) ? (((number - 1) / 8) >= 1) : false;

        this.number = number;

        var svg = document.createElementNS("http://www.w3.org/2000/svg", "svg");
        svg.setAttribute("viewBox", allowForShadow ? "0 0 120 120" : "0 0 105 100");
        svg.setAttribute("width", size);
        svg.setAttribute("preserveAspectRatio", "xMidYMid meet");
        var g = document.createElementNS("http://www.w3.org/2000/svg", "g");
        this.ballGraphic = g;
        var circle = document.createElementNS("http://www.w3.org/2000/svg", "circle");

        if (isStripe) {
            circle.setAttribute("cx", 50);
            circle.setAttribute("cy", 50);
            circle.setAttribute("r", 48);
            circle.setAttribute("style", "fill: white;");
            g.appendChild(circle);

            var path = document.createElementNS("http://www.w3.org/2000/svg", "path");
            path.setAttribute("d", "M 16 16 L 84 16 A 50 50 0 0 1 84 84 L 16 84  A 50 50 0 0 1 16 16 ");
            path.setAttribute("style", "fill: " + color + "; stroke-width: 1; stroke: grey;");
            g.appendChild(path);

            circle = document.createElementNS("http://www.w3.org/2000/svg", "circle");
            circle.setAttribute("cx", 50);
            circle.setAttribute("cy", 50);
            circle.setAttribute("r", 48);
            circle.setAttribute("style", "fill: transparent; stroke-width: 1; stroke: var(--ballOutline);");
            g.appendChild(circle);

        } else {
            circle.setAttribute("cx", 50);
            circle.setAttribute("cy", 50);
            circle.setAttribute("r", 48);
            circle.setAttribute("style", `fill: ${color}; stroke-width: 1; stroke: var(--ballOutline);`);
            g.appendChild(circle);
        }

        circle = document.createElementNS("http://www.w3.org/2000/svg", "circle");
        circle.setAttribute("cx", 50);
        circle.setAttribute("cy", 50);
        circle.setAttribute("r", 27);
        circle.setAttribute("style", "fill: white; stroke-width: 1; stroke: grey;");
        g.appendChild(circle);
        var text = document.createElementNS("http://www.w3.org/2000/svg", "text");
        text.setAttribute("x", 50);
        text.setAttribute("y", 53);
        text.setAttribute("text-anchor", "middle");
        text.setAttribute("dominant-baseline", "middle");
        text.setAttribute("font-weight", "bold");
        text.setAttribute("font-size", number > 9 ? "32px" : "40px");
        text.innerHTML = number;
        g.appendChild(text);
        svg.appendChild(g);

        this.element = svg;
    }
}

class BilliardBallWithState extends BilliardBall {

    constructor(number, size, clickFn, foulText) {
        super(number, size, true);

        const svg = this.element;
        svg.onclick = function () { clickFn(number)};
        let text = document.createElementNS("http://www.w3.org/2000/svg", "text");
        text.setAttribute("style", "visibility: hidden;");
        text.classList.add("dropShadow");
        text.setAttribute("x", 50);
        text.setAttribute("y", 50);
        text.setAttribute("text-anchor", "middle");
        text.setAttribute("dominant-baseline", "middle");
        text.setAttribute("font-size", "30px");
        text.setAttribute("fill", "red");
        text.setAttribute("stroke-width", "1");
        text.setAttribute("stroke", "white");
        text.innerHTML = foulText;
        svg.appendChild(text);
        this.foulText = text;
        text = document.createElementNS("http://www.w3.org/2000/svg", "text");
        text.setAttribute("style", "visibility: hidden;");
        text.classList.add("dropShadow");
        text.setAttribute("x", 40);
        text.setAttribute("y", 90);
        text.setAttribute("font-size", "80px");
        text.setAttribute("fill", "green");
        text.setAttribute("stroke-width", "1");
        text.setAttribute("stroke", "white");
        text.innerHTML = "✔";
        svg.appendChild(text);
        this.checkMark = text;

        this.showNormal();
    }

    dimElement(elem, dim) {
        if (dim) {
            elem.classList.remove("dropShadow");
            elem.classList.add("dimmed");
        } else {
            elem.classList.add("dropShadow");
            elem.classList.remove("dimmed");
        }
    }

    showElement(elem, show) {
        elem.style.visibility = show ? "visible" : "hidden";
    }

    showNormal() {
        this.dimElement(this.ballGraphic, false);
        this.showElement(this.foulText, false);
        this.showElement(this.checkMark, false);
    }

    showPocketed(checked) {
        this.dimElement(this.ballGraphic, true);
        this.showElement(this.foulText, false);
        this.showElement(this.checkMark, checked);
    }

    showFoul() {
        this.dimElement(this.ballGraphic, true);
        this.showElement(this.foulText, true);
        this.showElement(this.checkMark, false);
    }
}

    function updateBallState(number) {
        const currentBallState = match.ballStates[number - 1];
        const ball = balls[number];

        switch (currentBallState) {
            case "normal":
                ball.showNormal();
                break;

            case "dead":
                ball.showFoul();
                break;

            default:
                ball.showPocketed(currentBallState === "won");
                break;
        }
    }

Also, although not reflecting in the screen caps, it seems that cookies are not working correctly on iPhone, so I am wondering if I am handling them correctly – see onLoad function in NineBall.html and Preferences class in Billiards.js.

I need to understand what I am doing that is not functional/uniformly supported across browsers and what I need to do to fix it.

Chrome screen-cap (expected appearance):

Expected appearance (Chrome)


iPhone screen-cap (shows anomaly as described above):

Actual appearance (iPhone)

Could not append FormData in react

i am trying to append form data to send it to backend but could not do so, here are my usestates

  const [title, settitle] = useState();
  const [description, setdescription] = useState();
  const [image, setimage] = useState();

and here i am trying to append data in these states after having data in these states,

const data = new FormData();
      data.append("images", image.name);
      data.append("title", title);
      data.append("description", description);

i am new to react so can anyone tell me what am i doing wrong here ?

Automatically updating a page with new images in Symfony and PHP using Ajax and JavaScript

I’m trying to make a page that displays the images of my frames and display them one by one during the duration defined beforehand. I want my page to update automatically without reloading when I add new images.

I have this ajax request that reloads the page every minute but I want it to be done automatically.

**The Controller :
**

<?php

namespace AppController;

use AppEntityChanel;
use AppRepositoryChanelRepository;
use DateTime;
use DateTimeImmutable;
use SymfonyBundleFrameworkBundleControllerAbstractController;
use SymfonyComponentHttpFoundationJsonResponse;
use SymfonyComponentHttpFoundationResponse;
use SymfonyComponentRoutingAnnotationRoute;

class ChanelController extends AbstractController
{
    
    #[Route('/chanels', name: 'app_chanel')]
    public function index(ChanelRepository $repository): Response
    {
        $chanels = $repository->findBy([], ['name' => 'ASC']);

        return $this->render('chanel/index.html.twig', [
            'chanels' => $chanels,
        ]);
    }

    #[Route('/chanel/{id}', name: 'app_chanel_show', requirements: ['id' => "d+"]
    ,
        methods: ['GET']
    )]
    public function show(Chanel $chanel): Response
    {
        $frames = $chanel->getFrames();
        $currentDateTime = new DateTime();
        $activeFrames = [];
        $frameDurations = [];
    
        foreach ($frames as $frame) {
            $frameStartDate = $frame->getDateDeb();
            $frameEndDate = $frame->getDateFin();
    
            if ($currentDateTime >= $frameStartDate && $currentDateTime <= $frameEndDate && $frame->isIsPublic()) {
                $activeFrames[] = $frame;
                $frameDurations[] = $frame->getDuration();
            }
        }
    
        return $this->render('chanel/show.html.twig', [
            'chanel' => $chanel,
            'frames' => $activeFrames,
            'frameDurations' => $frameDurations,
        ]);
    }
    


    #[Route('/chanel/{id}/frames', name: 'app_chanel_frames', requirements: ['id' => "d+"]
    ,
        methods: ['GET']
    )]
    public function frames(Chanel $chanel): JsonResponse
    {
        $frames = $chanel->getFrames();
        $activeFrames = [];
        $frameDurations = [];
        $currentDateTime = new DateTime();

        foreach ($frames as $frame) {
            $frameStartDate = $frame->getDateDeb();
            $frameEndDate = $frame->getDateFin();

            if ($currentDateTime >= $frameStartDate && $currentDateTime <= $frameEndDate) {
                $activeFrames[] = $frame;
                $frameDurations[] = $frame->getDuration();
            }
        }
        $data = [
            'frames' => $activeFrames,
            'frameDurations' => $frameDurations,
        ];

        return new JsonResponse($data);
    }
}

**The view
**

{% extends 'base.html.twig' %}

{% block title %}Chanel {{ chanel.id }}{% endblock %}

{% block header %}{% endblock %}

{% block head %}

    {% block stylesheets %}
        <link href="{{ asset('css/chanel.css') }}" type="text/css" rel="stylesheet" />
        <link href="{{ asset('css/footer.css') }}" type="text/css" rel="stylesheet" />
    {% endblock %}

    {% block javascripts %}

        <script>
            var frameDurations = JSON.parse('{{ frameDurations|json_encode|raw }}');
        </script>
        <script src="https://code.jquery.com/jquery-3.6.0.min.js"></script>
        <script src="{{ asset('js/image.js') }}"></script>
        <script>
            function charger(){
                setTimeout( function(){
                    $.ajax({
                        url : '{{ path('app_chanel_frames', {id: chanel.id}) }}',
                        type : 'GET',
                        success : function(data){
                            if(data.success == false){
                                alert('erreur dans le rechargement')  
                            }else{
                                location.reload(true);
                            }
                        }
                    });

                    charger(); // on relance la fonction

                }, 60000); // on exécute le chargement toutes les minutes

            }
            charger();
        </script>


    {% endblock %}
{% endblock %}

{% block body %}

    <div class="frame__images">
        {% for frame in frames %}
            {% if frame.isPublic %}
                {% for image in frame.frameImages %}
                    {% if frame.frameImages is null %}
                        <img src="{{ asset('images/icone.png') }}" alt>
                    {% else %}
                        <img src="{{ vich_uploader_asset(image, 'imageFile') | imagine_filter('resizing') }}" alt>
                    {% endif %}
                {% endfor %}
            {% endif %}
        {% endfor %}
    </div>

    <footer>
        <h2>Ti Hebdo</h2>
    </footer>

{% endblock %}

**The javascript file that manages the image change
**

console.log('Script en cours...');

$(document).ready(function() {
  // Récupérer toutes les images des frames
  var images = $('.frame__images img');
  
  // Masquer toutes les images sauf la première
  images.not(':first').hide();

  // Définir l'index de l'image courante
  var currentImageIndex = 0;

  // Fonction pour afficher l'image suivante
  function showNextImage() {
    // Masquer l'image courante
    images.eq(currentImageIndex).hide();

    // Incrémenter l'index de l'image courante
    currentImageIndex++;

    // Vérifier si on atteint la fin des images
    if (currentImageIndex >= images.length) {
      currentImageIndex = 0; // Revenir au début
    }

    // Afficher l'image suivante
    images.eq(currentImageIndex).show();
  }

  // Définir l'intervalle pour changer d'image en utilisant la durée de chaque frame
  var totalDuration = frameDurations.reduce(function(a, b) {
    return a + b;
  }, 0); // Calculer la durée totale des frames

  setInterval(showNextImage, totalDuration * 1000);
});

set class’ private members to constructor arguments

class Foo {
  #one
  #two
  #three
  #four
  #five
  #six
  #seven
  #eight
  #nine
  #ten
  #eleven
  #twelve
  #thirteen
  #fourteen
  #fifteen
  #sixteen

  constructor(
    one,
    two,
    three,
    four,
    five,
    six,
    seven,
    eight,
    nine,
    ten,
    eleven,
    twelve,
    thirteen,
    fourteen,
    fifteen,
    sixteen
  ) {
    this.#one = one;
    this.#two = two;
    this.#three = three;
    this.#four = four;
    this.#five = five;
    this.#six = six;
    this.#seven = seven;
    this.#eight = eight;
    this.#nine = nine;
    this.#ten = ten;
    this.#eleven = eleven;
    this.#twelve = twelve;
    this.#thirteen = thirteen;
    this.#fourteen = fourteen;
    this.#fifteen = fifteen;
    this.#sixteen = sixteen;
  }
}

What’s a solution to this (anti?) pattern?

Google Business Profile API: Updating hotel information successfully but changes not reflected on hotel edit page

I am currently developing a web application in order to manage hotels on Google Business Profile, I am utilizing the Google OAuth2 and Google Business Profile API. The API is functioning correctly, and I am able to successfully update lodging information for a test business profile that is verified by Google. However, when I navigate to the hotel details page, I do not see the changes reflected.

My main concern is how to modify the hotel amenities on the Google Business Profile using my web application. While the API updates are not being reflected on the hotel’s edit page, I would like to find a solution to implement these changes through my web application. If you have any additional questions regarding my inquiry, please let me know, and I appreciate any assistance you can provide. Thank you!

I have attempted to update the lodging information by making HTTP requests using Postman, as well as through a ReactJS method that utilizes a backend endpoint to communicate with the Google Business Profile API. Despite these efforts, the changes made to the lodging information are not reflected on the hotel’s edit page in the Google Business Profile.

comment changer le barre de navigation aprés connexion en angular sans reloader la page [closed]

j’ai mon code TokenService dans j’ai mis les fonctions:getRoles() et isAuthenticated(),ou je le fait appel en ngOninit dans le componenet navbar pour gerer l’affichage selon le role,et si l’utilisateur connecté ou non :

export class LoginComponent implements OnInit {

  const userId = decodedToken.id;
  const userEmail = decodedToken.sub;
  const userRole = decodedToken.roles[0].authority;

  localStorage.setItem('token', token);
  localStorage.setItem('user_id', userId.toString());
  localStorage.setItem('user_email', userEmail);
  localStorage.setItem('user_role', userRole);
  console.log(userId, userEmail, userRole);

  if (userRole === 'USER') {
    this.router.navigateByUrl('/operations');
  } else if (userRole === 'ADMIN') {
    this.router.navigateByUrl('/customers');
  }
});

}
}

Mon TokenService :

  export class TokenService { isAuthenticated(): boolean {
const token = localStorage.getItem('token') ?? '';
return !this.jwtHelper.isTokenExpired(token); }                        getTokenPayload() {const token = localStorage.getItem('token'); const tokenPayload = token !== null ? jwtDecode(token) : {};return tokenPayload;} public loadAccessToken(): string | null {return localStorage.getItem('token'); } getRoles(): Observable<any> { const token = this.loadAccessToken();if (token) {
  const decodedToken = this.jwtHelper.decodeToken(token);
  const userRole = decodedToken.roles[0].authority;
  return of(userRole);}return of(null);}}

et le navbar ts:

export class NavbarComponent implements OnInit {isLoggedIn!: boolean;role: any constructor(private route: Router, private tokenService: TokenService) {} ngOnInit(): void {this.isLoggedIn = !!this.tokenService.isAuthenticated();this.tokenService.getRoles().subscribe((data) => {this.role = data; }).unsubscribe()}logout() {if (localStorage.getItem('token')) localStorage.clear();this.route.navigateByUrl('/login');this.isLoggedIn = false; }}

et en html:

 <mat-toolbar color="primary"><div class="left-section"><a href="" mat-button>Acceuil</a><a href="/customers" mat-button *ngIf="role == 'ADMIN' && isLoggedIn ">Clients</a </div><div class="spacer"></div><div class="right-section"><button [matMenuTriggerFor]="menu" *ngIf="isLoggedIn"> <mat-icon>person</mat-icon></button></div></mat-toolbar>

Why is my error message not displaying in my JavaScript meal maker project? [closed]

While learning JavaScript with Codecademy I’m stuck on a project called Meal Maker.
The project is to create a Function that takes input for a meal and its price and outputs it as Today’s Special.
But if the input in incorrect it will display an error message.
Everything is working as far as I can tell except for the error message. Even if I input incorrect variable types the error message does not display.

const menu = {
  _meal: '',
  _price: 0,

  set meal(mealToCheck) {
    if (typeof mealToCheck === 'string') {
      return this._meal = mealToCheck;
    }
  },

  set price(priceToCheck) {
    if (typeof priceToCheck === 'number') {
      return this._price = priceToCheck;
    }
  },

  get todaysSpecial() {
    if (this._meal && this._price) {
      return `Today's Special is ${this._meal} for $${this._price}!`
    } else {
      return 'Meal or price was not set correctly!'
    }
  }
};

menu._meal = 43;
menu._price = 'Fish'; 
console.log(menu.todaysSpecial);

What I tried was the code snippet above,

The results I receive are:
‘Today’s Special is 43 for $Fish!’.

When I thought it would display the error message ‘Meal or price was not set correctly!’.

How to manage edits in Yjs document based on access rights?

Imagine object like this

const project = { 
  editors:{'[email protected]':'owner', '[email protected]':'manager' },
  title:'myStackProject',
  article:'I love to ask questions'
}

In my case managers can’t edit title but they can edit article. So the problem is how to prevent project.title from edition made by managers.
I use Y.js & y-socket.io
Maybe you have already met the problem and know how to deal with it.

How to implement closeable dynamic tabs in React DevExtreme with automatic switch to parent tab on close?

enter image description here

I want to implement a tab system in DevExtreme React, where two tabs are static and each tab renders a TreeList component, while additional tabs are dynamically added upon clicking an icon in a row of the TreeList within one of the static tabs? Furthermore, I want these dynamically added tabs to be closeable. After closing a dynamically added tab, I would like to automatically switch back to the parent tab. What would be the recommended approach to achieve this functionality?

You can look at image for understanding.

enter image description here

I dynamically opened a tab and displayed the corresponding data. However, upon closing the tab, it doesn’t automatically return to the parent tab. Additionally, when the tab is closed, the tab title disappears(as it should be), but the data associated with it remains visible until another tab title is clicked.

Kindly guide me what i’m doing wrong.

Below is my code

import React, { useCallback, useEffect, useState } from 'react'
import './styles.css'
import PricingTreeList from './PricingTreeList'
import ResourcesTreeList from './ResourcesTreeList'
import { useDispatch, useSelector } from 'react-redux'
import { Sortable } from 'devextreme-react/sortable'
import TabPanel from 'devextreme-react/tab-panel'
import OpenNewTab from './OpenNewTab'
import { removeEstimateById } from '../../../../actions/EstimateActions/EstimateWorksheetAction'

const DynamicTabPanel = () => {
    const [selected, setSelected] = useState('btn1')
    const [content, setContent] = useState(<PricingTreeList />)

    const allWorksheets = useSelector((state) => state.estimateWorksheet.worksheets)
    const pricingTasks = useSelector((state) => state.estimateTask.tasks)
    const pricingResources = useSelector((state) => state.estimateResource.resources)

    const [openedSheets, setOpenedSheets] = useState(allWorksheets)

    const dispatch = useDispatch()
  
    const handleActive = (btn) => {
        setSelected(btn)
        setContent(getContent(btn))
    }
    // * Close Button Handler
    const closeButtonHandler = useCallback(
        (item) => {
            
            if (item && item.length > 0) {
                dispatch(removeEstimateById(item[0].projectId, item[0].taskId))
            } else {
                console.warn('Item is empty');
            }
        },
        [allWorksheets]
    )

    const getContent = (btn) => {
        switch (btn) {
            case 'btn1':
                return <PricingTreeList dataSource={pricingTasks} />
            case 'btn2':
                return <ResourcesTreeList dataSource={pricingResources} />
            case 'btn3':
                return allWorksheets.map((worksheetArray, index) => {
                    if (worksheetArray && worksheetArray.length > 0) {
                        return <OpenNewTab key={index} dataSource={worksheetArray} />
                    } else {
                        return null
                    }
                });

            default:
                return ''
        }
    }

    // * Render Title
    const renderTitle = useCallback((data) => {
        // let alreadyPushed = data.find(elem => elem.taskId).taskId === pricingTasks.find(element => element).id

        return (
            <>
                <div className='position-relative'>
                    <span>WS - New Task</span>
                    {<i
                        className='fal fa-times'
                        id='close-icon'
                        onClick={() => closeButtonHandler(data)}
                    />
                    }
                </div>
            </>
        )
    })

  
    return (
        <div>
            <div className='group-btn'>
                <button
                    type='button'
                    className={`tab-btn ${selected === 'btn1' ? 'active' : ''}`}
                    onClick={() => handleActive('btn1')}
                >
                    Pricing
                </button>
                <button
                    type='button'
                    className={`tab-btn ${selected === 'btn2' ? 'active' : ''}`}
                    onClick={() => handleActive('btn2')}
                >
                    Resources
                </button>

                <div onClick={() => handleActive('btn3')}>
                    {allWorksheets.length === 0 ? null : (
                        <Sortable
                            filter='.dx-tab'
                            data={allWorksheets}
                            itemOrientation='horizontal'
                            dragDirection='horizontal'
                        >
                            <TabPanel
                                dataSource={allWorksheets}
                                id='estimate-tabpanel'
                                itemTitleRender={renderTitle}
                                selectedIndex={-1}
                            ></TabPanel>
                        </Sortable>
                    )}
                </div>
            </div>
            <>{content}</>
        </div>
    )
}

export default DynamicTabPanel

How to avoid bias in large numbers in mathematical operations?

I am developing a React application. I’m doing tax calculations. There are 3 types of tax: otv, kdv and withholding. I can get these values ​​as amount or rate. Firstly, otv is calculated according to rate or amount. Then, kdv is calculated over the otv price. Finally, the withholding value is calculated only as a percentage on kdv. I have 2 problems with these calculations.

For example, I give the value of X and get the value of Y. I want to give the Y value and get the X value. I also want to do the operation in reverse.

First of all, if I do not get the otv or kdv values ​​in both rate or amount (For example, if it wants to be calculated as kdv rate, otv amount) there is an error in the calculation.

My second problem is that the withholding information is calculated over kdv, as I mentioned. But I am constantly experiencing minor deviations while calculating. For example, where I should get 100, I get 98. I couldn’t find my mistake.
Example = let the price be 100 – %10 ptv tax – %10 kdv tax and 5 withholding
When we trade according to the numbers I gave Otv : 100 x (10/100) : 110
Kdv : otv x (10 * 100) and witholding : kdv x (5/10) result : 115.5.
I want to give 115.5 and get 100 with the same numbers.

var tempTotal = 0;
var otvTotal = 0;
if (otv > 0) {
  if (otvType) {
    if (otvType === "rate") {
      var otvRate = 1 + otv / 100;
      otvTotal = Number(total / otvRate);
    } else if (otvType === "amount") {
      otvTotal = total - otv;
    }
  }
} else {
  otvTotal = total;
}
var holdingTotal = 0;
var valueOfWithholding = 0;
if (withholdingRate >= 0 || withholdingRate == null) {
  var withholding = withholdingRate ? withholdingRate : 0;
  var kdvRate = Number(1 + taxRate / 100);
  var withKdv = Number(otvTotal / kdvRate).toFixed(1);
  var withoutKdv = otvTotal - withKdv; // KDV'siz fiyat tevkifat için
  var valueOfWithholding;;
  if (withholdingRate > 0) {
    var holdingRate = (withholdingRate / 10);
    valueOfWithholding = (withoutKdv * holdingRate);
  } else {
    valueOfWithholding = 0;
  }
  tempTotal = otvTotal - withoutKdv  + valueOfWithholding;
}

Blazor Server, get return value from Async Java Function

Racking my brain trying to get this working, I can get synchronous JS values from JS to Blazor, but async doesn’t get sent over.

Let’s say I have the following code:

.razor

private async Task GetJSRemoteIP()
{
    string remoteIP = await JSRunTime.InvokeAsync<string>("getIPadr");
}

.js

function getIPadr() {
return "works!"
}

however, if I change the js to an async function with return, it never gets sent back to blazor, like so:

.js

async function getIPadr() {
const response = await fetch("https://api.ipify.org?format=json");
const jsonData = await response.json();
return jsonData;

}

What do I need to do to get the async function value back into blazor with return?

chrome: changes in sources/overrides are not applied?

I’ve set up the local Overrides under the sources Tab in Chrome, added console.logs in one of the js and put some breakpoints after them. After refreshing the page it stops at the breakpoints, but when I go to the Console tab, I don’t see anything.

On the Overrides tab I see a small notification at the file icon, saying 'Linked to source map ...', so I suppose that I did everything good, what do I still miss then?

I also tried to create some dummy variables, like const a=2; and put the breakpoint after, but on the Local Scope I don’t see it.

Any advice is appreciated,

Mat

Angular get “Failed to load module script: Expected a JavaScript module script but the server responded with a MIME type of “text/html” error on load

I added PWA to my angular app and after that, I made an error. When I open the site in browser it’s work correctly, but after closing the tab and reopening it, I have an error on the console that says “Failed to load module script: Expected a JavaScript module script but the server responded with a MIME type of “text/html”.

With this error, my site couldn’t load and I have a white page.

The interesting thing is that when I load with (ctrl+f5), the site works correctly again.

enter image description here