I'm trying to connect OpenAI API to my Vue.js project. Everything is OK but every time I try to POST request, I get a 429 status code (too many request) but I didn't even had the chance to make one. Any help?
Response:
{
"message": "Request failed with status code 429",
"name": "Error",
"stack": "Error: Request failed with status code 429\n at createError (C:\\Users\\sim\\Documents\\SC\\server\\node_modules\\axios\\lib\\core\\createError.js:16:15)\n at settle (C:\\Users\\sim\\Documents\\SC\\server\\node_modules\\axios\\lib\\core\\settle.js:17:12)\n at IncomingMessage.handleStreamEnd (C:\\Users\\sim\\Documents\\SC\\server\\node_modules\\axios\\lib\\adapters\\http.js:322:11)\n at IncomingMessage.emit (events.js:412:35)\n at endReadableNT (internal/streams/readable.js:1333:12)\n at processTicksAndRejections (internal/process/task_queues.js:82:21)",
"config": {
"transitional": {
"silentJSONParsing": true,
"forcedJSONParsing": true,
"clarifyTimeoutError": false
},
"transformRequest": [
null
],
"transformResponse": [
null
],
"timeout": 0,
"xsrfCookieName": "XSRF-TOKEN",
"xsrfHeaderName": "X-XSRF-TOKEN",
"maxContentLength": -1,
"maxBodyLength": -1,
"headers": {
"Accept": "application/json, text/plain, */*",
"Content-Type": "application/json",
"User-Agent": "OpenAI/NodeJS/3.1.0",
"Authorization": "Bearer secret",
"Content-Length": 137
},
"method": "post",
"data": "{\"model\":\"text-davinci-003\",\"prompt\":\"option-2\",\"temperature\":0,\"max_tokens\":3000,\"top_p\":1,\"frequency_penalty\":0.5,\"presence_penalty\":0}",
"url": "https://api.openai.com/v1/completions"
},
"status": 429
}
My method in Vue.js:
async handleSelect() {
try {
const res = await fetch("http://localhost:8000/", {
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: JSON.stringify({
question: this.selectedOption,
})
})
const data = await res.json();
console.log(data);
} catch {
console.log(data);
}
}
on server side
app.post("/", async (req, res) => {
try {
const question = req.body.question;
const response = await openai.createCompletion({
model: "text-davinci-003",
prompt: `${question}`,
temperature: 0, // Higher values means the model will take more risks.
max_tokens: 3000, // The maximum number of tokens to generate in the completion. Most models have a context length of 2048 tokens (except for the newest models, which support 4096).
top_p: 1, // alternative to sampling with temperature, called nucleus sampling
frequency_penalty: 0.5, // Number between -2.0 and 2.0. Positive values penalize new tokens based on their existing frequency in the text so far, decreasing the model's likelihood to repeat the same line verbatim.
presence_penalty: 0, // Number between -2.0 and 2.0. Positive values penalize new tokens based on whether they appear in the text so far, increasing the model's likelihood to talk about new topics.
});
// console.log(response);
res.status(200).send({
bot: response.data.choices[0].text,
});
} catch (error) {
// console.error(error);
res.status(500).send(error || "Something went wrong");
}
});
It's hard to say why your attempt was unsuccessful because you haven't added the full code. The code below works.
Frontend
HelloWorld.vue
<template>
<div class="hello"></div>
<select v-model="selected" #change="handleSelect()">
<option disabled value="">Please select one</option>
<option>Say this is a test</option>
<option>Say nothing</option>
</select>
<div class="container-selected">Selected: {{ selected }}</div>
<div class="container-data" v-if="showData">{{ showData.bot }}</div>
</template>
<script>
export default {
data: function () {
return {
selected: "",
showData: "",
};
},
methods: {
async handleSelect(data) {
try {
const res = await fetch("http://localhost:3000/", {
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: JSON.stringify({
question: this.selected,
}),
});
const data = await res.json();
this.showData = data;
console.log(data);
} catch {
console.log(data);
}
},
},
};
</script>
<style lang="scss">
.container-selected {
margin-top: 12px;
font-size: 20px;
}
.container-data {
margin-top: 24px;
font-size: 20px;
}
</style>
package.json
{
"name": "openai",
"version": "0.1.0",
"private": true,
"scripts": {
"serve": "vue-cli-service serve",
"build": "vue-cli-service build",
"lint": "vue-cli-service lint"
},
"dependencies": {
"register-service-worker": "^1.7.2",
"vue": "^3.2.13",
"vue-class-component": "^8.0.0-0",
"vue-router": "^4.0.3",
"vuex": "^4.0.0"
},
"devDependencies": {
"#typescript-eslint/eslint-plugin": "^5.4.0",
"#typescript-eslint/parser": "^5.4.0",
"#vue/cli-plugin-eslint": "~5.0.0",
"#vue/cli-plugin-pwa": "~5.0.0",
"#vue/cli-plugin-router": "~5.0.0",
"#vue/cli-plugin-typescript": "~5.0.0",
"#vue/cli-plugin-vuex": "~5.0.0",
"#vue/cli-service": "~5.0.0",
"#vue/eslint-config-typescript": "^9.1.0",
"eslint": "^7.32.0",
"eslint-config-prettier": "^8.3.0",
"eslint-plugin-prettier": "^4.0.0",
"eslint-plugin-vue": "^8.0.3",
"prettier": "^2.4.1",
"sass": "^1.32.7",
"sass-loader": "^12.0.0",
"typescript": "~4.5.5"
}
}
Backend
index.js
const express = require('express');
const app = express();
app.use(express.json());
const cors = require('cors');
app.use(cors());
app.post('/', async(req, res) => {
try {
const { Configuration, OpenAIApi } = require('openai');
const configuration = new Configuration({
apiKey: 'sk-xxxxxxxxxxxxxxxxxxxx'
});
const openai = new OpenAIApi(configuration);
const question = req.body.question;
await openai.createCompletion({
model: 'text-davinci-003',
prompt: question,
temperature: 0,
max_tokens: 7
})
.then((response) => {
console.log(response.data.choices[0].text);
res.status(200).send({ bot: response.data.choices[0].text });
})
.catch((err) => {
res.status(400).send({ message: err.message });
})
} catch (error) {
res.status(500).send(error || 'Something went wrong');
}
});
const PORT = process.env.PORT || 3000;
app.listen(PORT, () => {
console.log(`Server is running on port ${PORT}.`);
});
package.json
{
"name": "openai-server",
"version": "1.0.0",
"description": "Express server",
"main": "index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"author": "",
"license": "ISC",
"dependencies": {
"cors": "^2.8.5",
"express": "^4.18.2",
"nodemon": "^2.0.20",
"openai": "^3.1.0"
}
}
Output
This is the reason you are getting that error, your subscription or free plan has expired
enter image description here
Related
I can't get the token data using getToken({req, secret}), always return null.
Next JS 13.1.1 and next-auth 4.3.4
package.json:
{
"name": "frontend",
"version": "0.1.0",
"private": true,
"scripts": {
"dev": "next dev",
"build": "next build",
"start": "next start",
"lint": "next lint",
"deploy": "npx serverless"
},
"dependencies": {
"#emotion/react": "^11.10.0",
"#emotion/styled": "^11.10.0",
"#mui/icons-material": "^5.8.4",
"#mui/lab": "^5.0.0-alpha.95",
"#mui/material": "^5.10.0",
"#reduxjs/toolkit": "^1.8.4",
"animate.css": "^4.1.1",
"chart.js": "^3.9.1",
"cookie": "^0.5.0",
"html-to-image": "^1.11.4",
"jsonwebtoken": "^9.0.0",
"jspdf": "^2.1.0",
"moment": "^2.29.4",
"next": "^13.1.1",
"next-auth": "^4.3.4",
"react": "^18.2.0",
"react-chartjs-2": "^4.3.1",
"react-cookie": "^4.1.1",
"react-dom": "^18.2.0",
"react-dropzone": "^14.2.2",
"react-hook-form": "^7.34.1",
"react-redux": "^8.0.2",
"sass": "^1.54.4",
"swr": "^1.3.0",
"uuid": "^8.3.2"
},
"devDependencies": {
"#types/cookie": "^0.5.1",
"#types/jsonwebtoken": "^9.0.0",
"#types/node": "18.7.5",
"#types/react": "18.0.17",
"#types/react-dom": "18.0.6",
"#types/uuid": "^8.3.4",
"eslint": "8.22.0",
"eslint-config-next": "^13.1.1",
"typescript": "4.7.4"
}
}
[...nextauth].js:
import NextAuth, { NextAuthOptions } from "next-auth";
// Providers
import Credentials from "next-auth/providers/credentials";
// Services
import { authService, refreshAccessToken } from "../../../services";
export const authOptions: NextAuthOptions = {
providers: [
Credentials({
name: "Credentials",
credentials: {
username: {
label: "Username",
type: "text",
placeholder: "C.C.",
autoComplete: true,
},
password: {
label: "Password",
type: "password",
placeholder: "Type your password...",
autoComplete: true,
},
},
async authorize(credentials) {
return await authService({
username: credentials!.username,
password: credentials!.password,
});
},
}),
],
pages: {
signIn: "/auth/login",
},
session: {
strategy: "jwt",
maxAge: 60 * 60 * 7, // 7 hours
updateAge: 60 * 60 * 2,
},
callbacks: {
async jwt({ token, account, user }) {
if (user) {
token.accessToken = user.accessToken;
token.refreshToken = user.refreshToken;
if (account) {
switch (account.type) {
case "credentials":
token.user = user.user;
token.accessTokenExpires = user.accessTokenExpires;
break;
}
}
}
if (Date.now() / 1000 < (token.accessTokenExpires as number)) {
return token;
}
return await refreshAccessToken(token);
},
async session({ session, token }) {
session.accessToken = token.accessToken;
session.user = token.user as any;
return session;
},
},
// secret: process.env.NEXTAUTH_SECRET!,
secret: process.env.NEXTAUTH_SECRET,
};
export default NextAuth(authOptions);
and middleware.ts:
import { getToken } from "next-auth/jwt";
import { withAuth } from "next-auth/middleware";
import { NextResponse } from "next/server";
// Interfaces
import { IUser } from "./interfaces";
const secret = process.env.NEXTAUTH_SECRET;
export default withAuth(async function middleware(req) {
const token = await getToken({ req, secret }); // ALWAYS returns null
const { user } = (token as { user: IUser; accessToken: string }) || {};
const isAuth = !!token;
const isAuthPage = req.nextUrl.pathname.startsWith("/auth");
if (isAuthPage) {
if (isAuth) {
// return NextResponse.redirect(new URL(`/${user.hierarchy}`, req.url));
return NextResponse.redirect(new URL(`/role`, req.url));
}
return null;
}
if (!isAuth) {
let from = req.nextUrl.pathname;
if (req.nextUrl.search) {
from += req.nextUrl.search;
}
return NextResponse.redirect(new URL(`/auth/login`, req.url));
}
});
process.env.NEXTAUTH_SECRET = secret.
I tried to debug with nextAuth, but the middleware works fine when the isAuth is false (if i try to load protected route, middleware redirect to /auth), just fail when the getToken function try to get the cookie
to verify auth, what is wrong? :(
I'm new to vuejs and have implemented this example:
Auth0 vuejs and api example
It works just fine, but I run into some issues when trying to merge the vuejs code to my own project.
When loading the page requiring authentication, I get this error:
index.vue?4db4:11 Uncaught (in promise) TypeError: Cannot destructure property 'getAccessTokenSilently' of 'Object(...)(...)' as it is undefined.
The code for my page, looks like this:
<script>
import Layout from "../../../layouts/main.vue";
import { getProtectedResource } from "#/services/message.service";
import { ref } from "vue";
import { useAuth0 } from "#auth0/auth0-vue";
const message = ref("");
const getMessage = async () => {
const { getAccessTokenSilently } = useAuth0();
const accessToken = await getAccessTokenSilently();
const { data, error } = await getProtectedResource(accessToken);
if (data) {
message.value = JSON.stringify(data, null, 2);
}
if (error) {
message.value = JSON.stringify(error, null, 2);
}
};
getMessage();
export default {
components: {
Layout
},
data() {
return {
};
},
methods: {
rightcolumn() {
if (document.querySelector('.layout-rightside-col').classList.contains('d-none'))
{
document.querySelector('.layout-rightside-col').classList.remove('d-none')
} else {
document.querySelector('.layout-rightside-col').classList.add('d-none')
}
}
}
};
</script>
<template>
<Layout>
<p id="page-description">
<span
>This page retrieves a <strong>protected message</strong> from an
external API.</span
>
<span
><strong
>Only authenticated users can access this page.</strong
></span
>
</p>
<CodeSnippet title="Protected Message" :code="message" />
</Layout>
</template>
I've tried the example from the documentation provided here enter link description here
<script>
import Layout from "../../../layouts/main.vue";
//import { getProtectedResource } from "#/services/message.service";
//import { ref } from "vue";
import { useAuth0 } from "#auth0/auth0-vue";
export default {
setup() {
const { loginWithRedirect } = useAuth0();
return {
login: () => {
loginWithRedirect();
}
};
},
components: {
Layout
},
data() {
return {
};
},
methods: {
rightcolumn() {
if (document.querySelector('.layout-rightside-col').classList.contains('d-none')) {
document.querySelector('.layout-rightside-col').classList.remove('d-none')
} else {
document.querySelector('.layout-rightside-col').classList.add('d-none')
}
}
}
}
</script>
But still receives this error:
index.vue?4db4:11 Uncaught (in promise) TypeError: Cannot destructure
property 'loginWithRedirect' of 'Object(...)(...)' as it is undefined.
at setup (index.vue?4db4:11:1)
I'm registrering the plugin this way in main:
createApp(App)
.use(store)
.use(router)
.use(VueApexCharts)
.use(BootstrapVue3)
.component(VueFeather.type, VueFeather)
.use(Maska)
.use(Particles)
.use(i18n)
.use(
createAuth0({
domain: 'xyz.auth0.com',
client_id: 'secret',
redirect_uri: 'http://localhost:4040/callback',
audience: 'https://audience',
})
)
.use(vClickOutside).mount('#app');
My package.json file:
{
"name": "vuejs",
"version": "0.1.0",
"private": true,
"scripts": {
"serve": "vue-cli-service serve",
"build": "vue-cli-service build",
"lint": "vue-cli-service lint"
},
"dependencies": {
"#auth0/auth0-vue": "^1.0.2",
"#ckeditor/ckeditor5-build-classic": "^32.0.0",
"#ckeditor/ckeditor5-vue": "^2.0.1",
"#fullcalendar/bootstrap": "^5.10.1",
"#fullcalendar/core": "^5.10.1",
"#fullcalendar/daygrid": "^5.10.1",
"#fullcalendar/interaction": "^5.10.1",
"#fullcalendar/list": "^5.10.1",
"#fullcalendar/timegrid": "^5.10.1",
"#fullcalendar/vue3": "^5.10.1",
"#j-t-mcc/vue3-chartjs": "^1.2.0",
"#popperjs/core": "^2.11.2",
"#simonwep/pickr": "^1.8.2",
"#vue-leaflet/vue-leaflet": "^0.6.1",
"#vueform/multiselect": "^2.3.1",
"#vueform/slider": "^2.0.8",
"#vueform/toggle": "^2.0.1",
"#vuelidate/core": "^2.0.0-alpha.34",
"#vuelidate/validators": "^2.0.0-alpha.26",
"#zhuowenli/vue-feather-icons": "^5.0.2",
"aos": "^2.3.4",
"apexcharts": "^3.33.0",
"axios": "^0.27.2",
"bootstrap": "^5.2.1",
"bootstrap-vue-3": "^0.3.3",
"chart.js": "^3.7.0",
"click-outside-vue3": "^4.0.1",
"core-js": "^3.6.5",
"echarts": "^5.3.0",
"feather-icons": "^4.28.0",
"firebase": "^9.6.6",
"highlight.js": "^11.4.0",
"leaflet": "^1.7.1",
"lottie-web": "^5.8.1",
"maska": "^1.5.0",
"moment": "^2.29.1",
"node-sass": "6.0.1",
"particles.vue3": "^1.40.2",
"prismjs": "^1.26.0",
"sass-loader": "^10.2.1",
"simplebar": "^5.3.6",
"simplebar-vue3": "^0.1.5",
"sweetalert2": "^11.4.32",
"swiper": "^6.8.4",
"vue": "3.2.36",
"vue-router": "^4.0.15",
"vue-draggable-next": "^2.1.1",
"vue-easy-lightbox": "^1.3.0",
"vue-feather": "^2.0.0",
"vue-flatpickr-component": "^9.0.5",
"vue-i18n": "^9.2.0-beta.15",
"vue-prismjs": "^1.2.0",
"vue3-apexcharts": "^1.4.1",
"vue3-count-to": "^1.1.2",
"vue3-echarts": "^1.0.4",
"vue3-google-map": "^0.8.3",
"vue3-quill": "^0.2.6",
"vuevectormap": "^1.0.8",
"vuex": "^4.0.2",
"yarn": "^1.22.17"
},
"devDependencies": {
"#vue/cli-plugin-babel": "~4.5.0",
"#vue/cli-plugin-eslint": "~4.5.0",
"#vue/cli-service": "~4.5.0",
"#vue/compiler-sfc": "^3.0.0",
"babel-eslint": "^10.1.0",
"eslint": "^6.7.2",
"eslint-plugin-vue": "^7.0.0"
},
"eslintConfig": {
"root": true,
"env": {
"node": true
},
"extends": [
"plugin:vue/vue3-essential",
"eslint:recommended"
],
"parserOptions": {
"parser": "babel-eslint"
},
"rules": {}
},
"browserslist": [
"> 1%",
"last 2 versions",
"not dead"
]
}
Using #auth0/auth0-vue has a limitation. useAuth0 must be used in the setup hook. Read the documentation for info.
To add login to your application, use the loginWithRedirect function that is exposed on the return value of useAuth0, which you can access in your component's setup function.
<script>
import { ref } from "vue";
import { useAuth0 } from "#auth0/auth0-vue";
export default {
setup() {
const message = ref("");
const { getAccessTokenSilently } = useAuth0();
const getMessage = async () => {
const accessToken = await getAccessTokenSilently();
const { data, error } = await getProtectedResource(accessToken);
if (data) {
message.value = JSON.stringify(data, null, 2);
}
if (error) {
message.value = JSON.stringify(error, null, 2);
}
};
getMessage();
return {
message
}
},
...
}
</script>
<template>...</template>
I am trying to set up a graphql express server with apollo, express, typeorm, and graphql, however I am getting this error now that I have implemented the UserResolver.ts file. I have already tried installing graphql and even have downgraded it to 14.2.1 but it still doesn't work. Here is the source code:
index.ts
import "reflect-metadata";
import express from 'express';
import {ApolloServer} from 'apollo-server-express';
import { buildSchema } from "type-graphql";
import { UserResolver } from "./UserResolver";
(async () => {
const app = express();
app.get('/', (_req, res) => res.send('hello'))
const apolloServer = new ApolloServer({
schema: await buildSchema({
resolvers: [UserResolver]
})
});
// my line idk if it works
await apolloServer.start();
apolloServer.applyMiddleware({ app });
app.listen(4000, () => {
console.log("express server started");
});
})()
// createConnection().then(async connection => {
// console.log("Inserting a new user into the database...");
// const user = new User();
// user.firstName = "Timber";
// user.lastName = "Saw";
// user.age = 25;
// await connection.manager.save(user);
// console.log("Saved a new user with id: " + user.id);
// console.log("Loading users from the database...");
// const users = await connection.manager.find(User);
// console.log("Loaded users: ", users);
// console.log("Here you can setup and run express/koa/any other framework.");
// }).catch(error => console.log(error));
UserResolver.ts
import { Query, Resolver } from 'type-graphql';
#Resolver()
export class UserResolver{
#Query(() => String)
hello(){
return "hi";
}
}
ormconfig.json
{
"type": "postgres",
"host": "localhost",
"port": 5432,
"username": "postgres",
"password": "7434006a",
"database": "graphqldatabase",
"synchronize": true,
"logging": false,
"entities": [
"src/entity/**/*.ts"
],
"migrations": [
"src/migration/**/*.ts"
],
"subscribers": [
"src/subscriber/**/*.ts"
],
"cli": {
"entitiesDir": "src/entity",
"migrationsDir": "src/migration",
"subscribersDir": "src/subscriber"
}
}
package.json
{
"name": "backend",
"version": "0.0.1",
"description": "Awesome project developed with TypeORM.",
"devDependencies": {
"#types/express": "^4.17.13",
"#types/graphql": "^14.5.0",
"#types/node": "^8.0.29",
"ts-node": "3.3.0",
"typescript": "3.3.3333"
},
"dependencies": {
"#nestjs/common": "^8.2.3",
"#nestjs/core": "^8.2.3",
"#nestjs/typeorm": "^8.0.2",
"apollo-server-express": "^3.5.0",
"express": "^4.17.1",
"graphql": "^14.2.1",
"pg": "^8.4.0",
"reflect-metadata": "^0.1.10",
"rxjs": "^7.4.0",
"typeorm": "0.2.41"
},
"scripts": {
"start": "ts-node src/index.ts",
"typeorm": "node --require ts-node/register ./node_modules/typeorm/cli.js --config src/config/postgres.config.ts"
}
}
I'm experimenting with the Composition API with Vue3. But there were some points I couldn't find. The same code did not work in two different projects.
What I want to do in my own project is to take the data through the API and use it according to what is required. In short, do the necessary get/post operations. I got this API from Vue's own example.
This is the first project code, package.json and error message
<template>
<div class="home">
<div v-for="datas in data" :key="datas.description">
{{ datas.description }}
</div>
</div>
</template>
<script lang="ts">
import { Options, Vue } from "vue-class-component";
import axios from "axios";
import { ref } from "vue";
#Options({
props: {
msg: String,
},
})
export default class HelloWorld extends Vue {
setup() {
let data = ref([]);
axios
.get("https://api.coindesk.com/v1/bpi/currentprice.json")
.then((res) => {
data.value = res.data.bpi;
});
}
}
</script>
{
"name": "api-project",
"version": "0.1.0",
"private": true,
"scripts": {
"serve": "vue-cli-service serve",
"build": "vue-cli-service build",
"lint": "vue-cli-service lint"
},
"dependencies": {
"axios": "^0.21.1",
"core-js": "^3.6.5",
"vue": "^3.0.0",
"vue-class-component": "^8.0.0-0",
"vue-router": "^4.0.0-0"
},
"devDependencies": {
"#vue/cli-plugin-babel": "~4.5.0",
"#vue/cli-plugin-router": "~4.5.0",
"#vue/cli-plugin-typescript": "~4.5.0",
"#vue/cli-service": "~4.5.0",
"#vue/compiler-sfc": "^3.0.0",
"node-sass": "^4.12.0",
"sass-loader": "^8.0.2",
"typescript": "~4.1.5"
},
"browserslist": [
"> 1%",
"last 2 versions",
"not dead"
]
}
Vue warn
This is the second project code, package.json, and data
<template>
<div v-for="datas in data" :key="datas.description">
{{ datas.description }}
</div>
</template>
<script lang="ts">
import axios from "axios";
import { ref } from "vue";
export default {
name: "HelloWorld",
setup() {
let data = ref([]);
axios.get("https://api.coindesk.com/v1/bpi/currentprice.json").then((res) => {
data.value = res.data.bpi;
});
return {
data,
};
},
}
</script>
{
"name": "test-api",
"version": "0.1.0",
"private": true,
"scripts": {
"serve": "vue-cli-service serve",
"build": "vue-cli-service build",
"lint": "vue-cli-service lint"
},
"dependencies": {
"axios": "^0.21.1",
"core-js": "^3.6.5",
"vue": "^3.0.0"
},
"devDependencies": {
"#vue/cli-plugin-babel": "~4.5.0",
"#vue/cli-plugin-eslint": "~4.5.0",
"#vue/cli-service": "~4.5.0",
"#vue/compiler-sfc": "^3.0.0",
"babel-eslint": "^10.1.0",
"eslint": "^6.7.2",
"eslint-plugin-vue": "^7.0.0",
"node-sass": "^4.12.0",
"sass-loader": "^8.0.2",
"typescript": "~4.1.5"
},
"eslintConfig": {
"root": true,
"env": {
"node": true
},
"extends": [
"plugin:vue/vue3-essential",
"eslint:recommended"
],
"parserOptions": {
"parser": "babel-eslint"
},
"rules": {}
},
"browserslist": [
"> 1%",
"last 2 versions",
"not dead"
]
}
my data
Could there be an error in my Composition API usage? I've heard that in some videos, "then" is not used for the Composition API. But that's the only way I was able to pull the data from the API.
If my solution is wrong, what method should it be, I'm new at Vuejs can you help?
You need to return the variables from the setup function so that they can be accessed from within the template.
If setup returns an object, the properties on the object can be
accessed in the component's template, as well as the properties of the
props passed into setup:
setup() {
let data = ref([]);
axios
.get("https://api.coindesk.com/v1/bpi/currentprice.json")
.then((res) => {
data.value = res.data.bpi;
});
// return the data as an object
return {
data
}
}
Read more about this in the official vue doc
You can create api dir inside src folder and then inside api dir create a file api.ts and put this code
export async function callApi(endpoint :string, method :string){
return await fetch(endpoint,{
method:method,
headers: {
'Content-type': 'application/json; charset=UTF-8',
},
}).then(async response => {
const resData = await response.json()
if (!response.ok) {
// do something to determine request is not okay
resData.isSuccess = false
}
return resData
}).catch(error => {
console.log("callApi in api.ts err")
console.log(error)
throw error
})
}
Go to you component and use this code
<template>
<div v-for="(item,i) in data.records" v-bind:key="i">
{{ item.chartName}}
</div>
</template>
<script>
import {onMounted,reactive} from "vue"
import {callApi} from "#/api/api"
export default{
name:'MyComponent',
setup() {
const data = reactive({
records: [],
})
onMounted( async() =>{
getRecords()
})
const getRecords = async() => {
let resData = await callApi('https://api.coindesk.com/v1/bpi/currentprice.json', 'GET')
data.records = resData
}
return {
data,
}
}
}
</script>
enter code here
I have a repository with a simple index.js:
(function() {
"use strict";
var angular = require('angular');
})();
I use gulp to bundle (full file down below in Edit):
gulp.task('browserify', function() {
return browserify({
entries: './dist/childRepository.js',
insertGlobals : true
})
.transform(to5ify)
.bundle()
.on('error', errorWarning)
.pipe(source('childRepository.bundle.js'))
.pipe(buffer())
.pipe(sourcemaps.init({loadMaps: true}))
.pipe(sourcemaps.write('./'))
.pipe(gulp.dest('dist'))
});
This creates my bundle file in the correct order and runs just fine in the browser. Now in another repository I made the first a dependency using npm.
npm install childRepository.git --save
In the second repository I created another index.js:
(function() {
"use strict";
var angular = require('angular');
var childRepository = require('childrepository');
})();
I have a similar gulpfile for browserify and bundling however it fails with an error:
events.js:160
throw er; // Unhandled 'error' event
^
Error: Cannot find module './angular' from '/Users/jrquick/uabshp/childRepository/dist'
at /Users/jrquick/node_modules/browser-resolve/node_modules/resolve/lib/async.js:55:21
at load (/Users/jrquick/node_modules/browser-resolve/node_modules/resolve/lib/async.js:69:43)
at onex (/Users/jrquick/node_modules/browser-resolve/node_modules/resolve/lib/async.js:92:31)
at /Users/jrquick/node_modules/browser-resolve/node_modules/resolve/lib/async.js:22:47
at FSReqWrap.oncomplete (fs.js:123:15)
I have tried several setups, adding source maps, flipping flags but cannot get around this error. Does anyone have any advice? Thanks.
Edit, my package.json for the childRepository:
{
"name": "childRepository",
"version": "1.0.0",
"description": "",
"main": "./dist/childRepository.bundle.js",
"directories": {
"example": "example"
},
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"repository": {
"type": "git",
"url": "git+ssh://git#bitbucket.org/uabshp/childRepository.git"
},
"author": "",
"license": "ISC",
"homepage": "https://bitbucket.org/uabshp/childRepository#readme",
"devDependencies": {
"6to5ify": "^4.1.1",
"gulp": "^3.9.1",
"gulp-concat": "^2.6.1",
"gulp-jshint": "^2.0.4",
"gulp-rename": "^1.2.2",
"gulp-sass": "^3.0.0",
"gulp-sourcemaps": "^2.6.0",
"gulp-uglify": "^2.0.0",
"jshint": "^2.9.4",
"vinyl-buffer": "^1.0.0",
"vinyl-source-stream": "^1.1.0"
},
"dependencies": {
"angular": "^1.6.0"
}
}
package.json for paren repository:
{
"name": "parentrepository",
"version": "1.0.0",
"description": "### How do I get set up? ###",
"main": "./dist/parentRepository.bundle.js",
"directories": {
"example": "example"
},
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"repository": {
"type": "git",
"url": "git+ssh://git#bitbucket.org/uabshp/parentRepository.git"
},
"author": "",
"license": "ISC",
"homepage": "https://bitbucket.org/uabshp/parentRepository#readme",
"devDependencies": {
"6to5ify": "^4.1.1",
"gulp": "^3.9.1",
"gulp-concat": "^2.6.1",
"gulp-jshint": "^2.0.4",
"gulp-rename": "^1.2.2",
"gulp-sass": "^3.0.0",
"gulp-sourcemaps": "^2.6.0",
"gulp-uglify": "^2.0.0",
"jshint": "^2.9.4",
"vinyl-buffer": "^1.0.0",
"vinyl-source-stream": "^1.1.0"
},
"dependencies": {
"angular": "^1.6.4",
"childRepository": "git+ssh://git#bitbucket.org/uabshp/childRepository.git"
}
}
gulpfile.js (same for both besides name):
var gulp = require('gulp');
var concat = require('gulp-concat');
var browserify = require('browserify');
var buffer = require('vinyl-buffer');
var jshint = require('gulp-jshint');
var rename = require('gulp-rename');
var sass = require('gulp-sass');
var source = require('vinyl-source-stream');
var sourcemaps = require('gulp-sourcemaps');
var to5ify = require('6to5ify');
var uglify = require('gulp-uglify');
gulp.task('sass', function() {
return gulp.src('sass/*.sass')
.pipe(sass())
.pipe(gulp.dest('dist/css'));
});
gulp.task('lint', function() {
return gulp.src('src/**/*.js')
.pipe(jshint())
.pipe(jshint.reporter('default'));
});
gulp.task('scripts', function() {
return gulp.src('src/*.js')
.pipe(concat('childRepository.js'))
.pipe(gulp.dest('dist'))
.pipe(rename('childRepository.min.js'))
.pipe(uglify())
.pipe(gulp.dest('dist'));
});
gulp.task('browserify', function() {
return browserify({
entries: './dist/childRepository.js',
insertGlobals: true,
standAlone: true
})
.transform(to5ify)
.bundle()
.on('error', errorWarning)
.pipe(source('childRepository.bundle.js'))
.pipe(buffer())
.pipe(sourcemaps.init({loadMaps: true}))
.pipe(sourcemaps.write('./'))
.pipe(gulp.dest('dist'))
});
gulp.task('watch', function() {
gulp.watch('src/*.js', ['build']);
gulp.watch('dist/childRepository.js', ['browserify']);
gulp.watch('sass/*.sass', ['sass']);
});
gulp.task('build', [
'sass',
'lint',
'scripts',
'browserify'
]);
gulp.task('default', [
'build',
'watch'
]);
function errorWarning(error) {
console.log(error.toString());
this.emit('end');
}
I solved this by install derequire: npm install gulp-derequire --save-dev
Then added to my gulpfile.js:
gulp.task('browserify', function() {
return browserify('./dist/uabError.js')
.transform(to5ify)
.bundle()
.on('error', errorWarning)
.pipe(source('uabError.bundle.js'))
.pipe(derequire())
.pipe(buffer())
.pipe(sourcemaps.init({loadMaps: true}))
.pipe(sourcemaps.write('./'))
.pipe(gulp.dest('dist'))
});
This does cause a problem where I get a warning about attempting to load angular more than once. I also have another work around that does not require derequire. Just set ignoreMissing to true.
gulp.task('browserify', function() {
return browserify('./dist/uabError.js', { ignoreMissing: true })
.transform(to5ify)
.bundle()
.on('error', errorWarning)
.pipe(source('uabError.bundle.js'))
.pipe(buffer())
.pipe(sourcemaps.init({loadMaps: true}))
.pipe(sourcemaps.write('./'))
.pipe(gulp.dest('dist'))
});