I am trying to go through a tutorial (link below) to learn vue and firebase. There is a main dashboard page with a list of components, and I have gotten that to display a list of employees. Then there is a view employee component. When I started to build that, and just loaded data, I started getting this error:
Uncaught FirebaseError {code: "app/duplicate-app", message: "Firebase:
Firebase App named '[DEFAULT]' already exists (app/duplicate-app).",
name: "[DEFAULT]", stack: "[DEFAULT]: Firebase: Firebase App named
'[DEFAULT]…0)↵ at fn (http://localhost:8081/app.js:89:20)"}
The firebase code I added to view employee is as follows:
import db from "./firebaseInit.js";
export default {
name: "view-employee",
data() {
return {
employee_id: null,
name: null,
dept: null,
position: null
};
},
beforeRouteEnter(to, from, next) {
db
.collection("employees")
.where("employee_id", "==", to.params.employee_id),
get().then(querySnapShot => {
querySnapShot.forEach(doc => {
next(vm => {
vm.employee_id = doc.data().employee_id
vm.name = doc.data().name
vm.dept = doc.data().dept
vm.position = doc.data().position
})
});
});
}
};
When I comment out this script on the view employee page, the error goes away. From what I can tell, I have done everything the same as the tutorial in the video, and as my buddy who did the same project.
There is also a warning, which may be related, which states as follows:
There are multiple modules with names that only differ in casing. This
can lead to unexpected behavior when compiling on a filesystem with
other case-semantic. Use equal casing. Compare these module
identifiers: *
/Users/jdurell/code/employeemanager/node_modules/babel-loader/lib/index.js!/Users/jdurell/code/employeemanager/src/components/FirebaseInit.js
I am working on this tutorial / project:
https://www.youtube.com/watch?v=cjEzK4me1k8&index=4&list=PLillGF-RfqbYsOOycB67Raf9dwmL6Y31M
Nemesv had the correct answer. It was a casing issue. I had the issue FirebaseInit on the other component. I changed that to firebaseInit so it was the same case on both components, and the error resolved. Thanks!
Related
I just started playing around with strapi using it for my next project with nextjs and i got stuck a little bit on the slug part.
I have installed the slugify plugin in the strapi admin panel, restarted the server and in the roles(permissions) section i enabled it for both authenticated and public roles.After this i created a collection type name Blog. I added some fields to it title, content, cover, slug(short text).
After this i created some blog posts and listed them out on the page. The problem began when i tried to access the blog post using the slug:
`${process.env.NEXT_PUBLIC_STRAPI_URL}/slugify/slugs/blog/${slug}?populate=*`,
The url is ok as the slug part is populated and is the value that i have given the slug field when created the blog post. The error that i get is the following:
blog model name not found, all models must be defined in the settings and are case sensitive.
The problem is that the slugify plugin is trying to match the model name to the existing ones and its not finding it so throws this error.
I started to dig a little bit deeper and began to console log in the slugify plugin inside strapi node_module:
module.exports = ({ strapi }) => ({
async findSlug(ctx) {
const { models } = getPluginService(strapi, 'settingsService').get();
const { modelName, slug } = ctx.request.params;
const { auth } = ctx.state;
console.log(getPluginService(strapi, 'settingsService').get());
isValidFindSlugParams({
modelName,
slug,
models,
});
As you can see it should container a models param aswell that should contain all the current models created in strapi. However the model paramateres comes back as an empty object, its like the plugin does not see the created collections.
The collections were created after the instalation of the slugify plugin.
I am developing on localhost using sqlite with strapi v4.
Any ideas why is this happening? Anyone else encountered this error?
Thanks,
Trix
Firstly, you have to install Slugify plugin.
After that you have to do some config steps.
To do all of that:
As you mentioned, you found Slugify folder in node_modules so you can skip first step:
npm install strapi-plugin-slugify
in the ./config/ folder create a file named plugins.js
./config/plugins.js
Paste this code there it will let you see the endpoint path in the right side of the screen:
module.exports = ({ env }) => ({
// ...
slugify: {
enabled: true,
config: {
contentTypes: {
blog: { //write what your collection type's name is this case we should use "blog"
field: "slug",
references: "title",
},
},
},
},
// ...
});
The endpoint example
fetcher(`${API}/slugify/slugs/blog/${slug}`)
When I test my React Native app that un my firebase config file
const auth = initializeAuth(app, {
persistence: getReactNativePersistence(AsyncStorage),
});
I get the error message: Cannot find module '#firebase/auth/react-native' from 'node_modules/firebase/auth/react-native/dist/index.cjs.js'
The app works fine in runtime, but doesn't seem to work during tests.
Any ideas to what this error could be caused by?
I was having the same issue this morning. Did you get it resolved?
I found that creating a file in the mocks directory called #firebase/auth/react-native.js and exporting a named function getReactNativePersistence resolved the issue (for now) for me. It's just a dummy function at this point, but my tests run.
__mocks__/#firebase/auth/react-native.js
export const getReactNativePersistence = () => {
return;
};
I have a nuxt application. One of the components in it's mounted lifecycle hook is requesting a value from the state store, this value is retrieved from local storage. The values exist in local storage however the store returns it as undefined. If I render the values in the ui with {{value}}
they show. So it appears that in the moment that the code runs, the value is undefined.
index.js (store):
export const state = () => ({
token: process.browser ? localStorage.getItem("token") : undefined,
user_id: process.browser ? localStorage.getItem("user_id") : undefined,
...
Component.vue
mounted hook:
I'm using UserSerivce.getFromStorage to get the value directly from localStorage as otherwise this code block won't run. It's a temporary thing to illustrate the problem.
async mounted() {
// check again with new code.
if (UserService.getFromStorage("token")) {
console.log("user service found a token but what about store?")
console.log(this.$store.state.token, this.$store.state.user_id);
const values = await ["token", "user_id"].map(key => {return UserService.getFromStorage(key)});
console.log({values});
SocketService.trackSession(this, socket, "connect")
}
}
BeforeMount hook:
isLoggedIn just checks that the "token" property is set in the store state.
return !!this.$store.state.token
beforeMount () {
if (this.isLoggedIn) {
// This runs sometimes??? 80% of the time.
console.log("IS THIS CLAUSE RUNNING?");
}
}
video explanation: https://www.loom.com/share/541ed2f77d3f46eeb5c2436f761442f4
OP's app is quite big from what it looks, so finding the exact reason is kinda difficult.
Meanwhile, setting ssr: false fixed the errors.
It raised more, but they should probably be asked into another question nonetheless.
My Main goal is to create an Electron App (Windows) that locally stores data in an SQLite Database. And because of type safety I choose to use the Prisma framework instead of other SQLite Frameworks.
I took this Electron Sample Project and now try to include Prisma. Depending on what I try different problems do arrise.
1. PrismaClient is unable to be run in the Browser
I executed npx prisma generate and then try to execute this function via a button:
import { PrismaClient } from '#prisma/client';
onSqlTestAction(): void {
const prisma = new PrismaClient();
const newTestObject = prisma.testTable.create(
{
data: {
value: "TestValue"
}
}
);
}
When executing this in Electron I get this:
core.js:6456 ERROR Error: PrismaClient is unable to be run in the browser.
In case this error is unexpected for you, please report it in https://github.com/prisma/prisma/issues
at new PrismaClient (index-browser.js:93)
at HomeComponent.onSqlTestAction (home.component.ts:19)
at HomeComponent_Template_button_click_7_listener (template.html:7)
at executeListenerWithErrorHandling (core.js:15281)
at wrapListenerIn_markDirtyAndPreventDefault (core.js:15319)
at HTMLButtonElement.<anonymous> (platform-browser.js:568)
at ZoneDelegate.invokeTask (zone.js:406)
at Object.onInvokeTask (core.js:28666)
at ZoneDelegate.invokeTask (zone.js:405)
at Zone.runTask (zone.js:178)
It somehow seems logical that Prisma cannot run in a browser. But I actually build a native app - with Electron that embeds a Browser. It seems to be a loophole.
2. BREAKING CHANGE: webpack < 5 used to include polyfills
So i found this Question: How to use Prisma with Electron
Seemed to be exactly what I looked for. But the error message is different (Debian binaries were not found).
The solution provided is to generate the prisma artifacts into the src folder instead of node_modules - and this leads to 19 polyfills errors. One for example:
./src/database/generated/index.js:20:11-26 - Error: Module not found: Error: Can't resolve 'path' in '[PATH_TO_MY_PROJECT]\src\database\generated'
BREAKING CHANGE: webpack < 5 used to include polyfills for node.js core modules by default.
This is no longer the case. Verify if you need this module and configure a polyfill for it.
If you want to include a polyfill, you need to:
- add a fallback 'resolve.fallback: { "path": require.resolve("path-browserify") }'
- install 'path-browserify'
If you don't want to include a polyfill, you can use an empty module like this:
resolve.fallback: { "path": false }
And this repeats with 18 other modules. Since the error message to begin with was different I also doubt that this is the way to go.
I finally figured this out. What I needed to understand was, that all Electron apps consist of 2 parts: The Frontend Webapp (running in embedded Chromium) and a Node backend server. Those 2 parts are called IPC Main and IPC Renderer and they can communicate with each other. And since Prisma can only run on the main process which is the backend I had to send my SQL actions to the Electron backend and execute them there.
My minimal example
In the frontend (I use Angular)
// This refers to the node_modules folder of the Electron Backend, the folder where the main.ts file is located.
// I just use this import so that I can use the prisma generated classes for type safety.
import { TestTable } from '../../../app/node_modules/.prisma/client';
// Button action
onSqlTestAction(): void {
this.electronService.ipcRenderer.invoke("prisma-channel", 'Test input').then((value) => {
const testObject: TestTable = JSON.parse(value);
console.log(testObject);
});
The sample project I used already had this service to provide the IPC Renderer:
#Injectable({
providedIn: 'root'
})
export class ElectronService {
ipcRenderer: typeof ipcRenderer;
webFrame: typeof webFrame;
remote: typeof remote;
childProcess: typeof childProcess;
fs: typeof fs;
get isElectron(): boolean {
return !!(window && window.process && window.process.type);
}
constructor() {
// Conditional imports
if (this.isElectron) {
this.ipcRenderer = window.require('electron').ipcRenderer;
this.webFrame = window.require('electron').webFrame;
this.childProcess = window.require('child_process');
this.fs = window.require('fs');
// If you want to use a NodeJS 3rd party deps in Renderer process (like #electron/remote),
// it must be declared in dependencies of both package.json (in root and app folders)
// If you want to use remote object in renderer process, please set enableRemoteModule to true in main.ts
this.remote = window.require('#electron/remote');
}
}
And then in the Electron backend I first added "#prisma/client": "^3.0.1" to the package.json (for the Electron backend not the frontend). Then I added to the main.ts this function to handle the requests from the renderer:
// main.ts
ipcMain.handle("prisma-channel", async (event, args) => {
const prisma = new PrismaClient();
await prisma.testTable.create(
{
data: {
value: args
}
}
);
const readValue = await prisma.testTable.findMany();
return JSON.stringify(readValue);
})
This way of simply adding the IPC Main handler in the main.ts file of course is a big code smell but usefull as minimal example. I think I will move on with the achitecture concept presented in this article.
I want to use Cordova Firebase Dynamiclinks plugin : https://github.com/chemerisuk/cordova-plugin-firebase-dynamiclinks#installation in my Ionic 4 App.
There is an Ionic-native-plugin usage for this too : npm install #ionic-native/firebase-dynamic-links and usage :
import { FirebaseDynamicLinks } from '#ionic-native/firebase-dynamic-links/ngx';
constructor(private firebaseDynamicLinks: FirebaseDynamicLinks) { }
...
this.firebaseDynamicLinks.onDynamicLink()
.subscribe((res: any) => console.log(res), (error:any) => console.log(error));
Issue is : I want to use createDynamicLink(parameters) method available in Cordova Firebase Dynamiclinks plugin but Ionic-native-plugin says
Property 'createDynamicLink' does not exist on type 'FirebaseDynamicLinks'.
Therefore, I need to use Cordova Firebase Dynamiclinks directly and I tried doing using it like
import { cordova } from '#ionic-native/core';
...
cordova.plugins.firebase.dynamiclinks.createDynamicLink({
link: "https://google.com"
}).then(function(url) {
console.log("Dynamic link was created:", url);
});
But got error
Property 'plugins' does not exist on type '(pluginObj: any, methodName: string, config: CordovaOptions, args: IArguments | any[]) => any'.
Also tried removing import
cordova.plugins.firebase.dynamiclinks.createDynamicLink({
link: "https://google.com"
}).then(function(url) {
console.log("Dynamic link was created:", url);
});
And got this
Property 'firebase' does not exist on type 'CordovaPlugins'.
What is the correct usage of cordova plugins?
Update
Ionic-native-plugin now contains all the methods available in Cordova Firebase Dynamiclinks plugin.
I believe this is more fitting of a comment, but I don't quite have the reputation for it yet.
Currently, there is a PR open in the #ionic-team/ionic-native repo (here). This exposes the extra methods, but until then you can use the original repo here to get your desired effect. In order to install the repo you will have to follow the directions in the Developer guide here. Cheers!
I have developed an ionic 5 app that uses Firebase Dynamic Links and it works great but it took some effort. I watched videos to understand how Firebase Dynamic Links work but there is certainly much that is not shown.
To answer the original question you can always manually create a dynamic link which is what I do in our solution. We created a dynamic link that would help users onboard (register an account). Our dynamic link has custom onboardingId which originates from the backend process and the link is presented to the user via SMS text message.
This is in app.component.ts constructor
Here is some code that happens when the user clicks the dynamic link:
// Handle the logic here after opening the app (app is already installed) with the Dynamic link
this.firebaseDynamicLinks.onDynamicLink().subscribe((res: any) => {
console.log('app was opened with dynamic link');
console.log(res);
/* This only fires on subsequent calls and not on app start 20220208 STR
console.log(JSON.stringify(res)); //"{"deepLink":"https://localhost/onboard?onboardingId=8ed634b0-53b7-4a0f-b67e-12c06019982a","clickTimestamp":1643908387670,"minimumAppVersion":0}"
var dynamicLink = JSON.parse(JSON.stringify(res));
var deepLink = dynamicLink.deepLink;
console.log(deepLink);
if (deepLink.indexOf("onboard")>=0){
this.isOnboarding = true;
}
alert("deepLink ="+ deepLink);
*/
}, (error:any) => {
console.log(error)
});
I originally thought that Firebase handles all of the magic if the user doesn't have the app installed. I was wrong! You MUST also handle the code to pickup the dynamic link after the app is installed.
The code below will read the dynamic link from the clipboard and survives the app install process. Placed in app.component.ts ngOnInit().
this.platform.ready().then(() => {
this.firebaseDynamicLinks.getDynamicLink().then((data) => {
//added 20220208 STR try to help open the deep link if app is just installed
if (data != null) {
console.log(JSON.stringify(data));
//alert("initializeApp():"+JSON.stringify(data));
var dynamicLink = JSON.parse(JSON.stringify(data));
var deepLink = dynamicLink.deepLink;
console.log("initializeApp():"+deepLink);
if (deepLink != "") {
if (deepLink.indexOf("onboard")>=0){
this.isOnboarding = true;
this.deepLinkToOnboard(deepLink);
}
}
}
});}
So to handle dynamic links after you have the Firebase plugin installed, you must have two sections of code; one for handling if the app is already installed and another for handling the dynamic link if the app is not installed.