I'm having trouble with axios get and post requests in real host - vue.js

When I'm on the local server localhost:8080 in vue project everything is great, but when I deploy the project to my real host I get the problem
mounted(){
axios.get('http://localhost/online-store/src/database_api/Admin/recent_product.php')
.then((res) => {
this.products= res.data
console.log(res.data)
})
},

configure your axios in main.js (entry point )
axios.create({
baseURL: process.env.VUE_APP_BASE_URL
})
Then directly call api ..it will append base url based on your env parameter
axios('/online-store/src/database_api/Admin/recent_product.php')
Note : Don't forget to add .env as per environment

Related

vue app calls the backend from the client origin (ip+port) but not from the frontend server

I am new to vue and maybe I miss some fundamental concept here but I am not able to force my vue app to call the backend from the frontend server origin (ip:port). It seems that the API calls arriving from the client IPs instead - cause an issue that the backend CORS control cannot work.
I try to create a simple hello-world app and host a separate backend and frontend server in a docker container on a NAS running at local network. The ip of the NAS on the local network is 192.168.0.150. I mapped the port: 5000 to the backend and 6080 to the frontend.
I use python fastAPI as a backend and vuejs as a frontend. everyting works fine if I allow all the origins in the fastapi.middleware.cors setting :
Backend - fastapi.middleware.cors settings :
app.add_middleware(
CORSMiddleware,
allow_origins=["*"],
allow_credentials=True,
allow_methods=["*"],
allow_headers=["*"],
)
#app.get("/")
def home(request:Request):
client_host = request.client.host
client_port= request.client.port
return {"message": "Hello, World!","client_host": client_host,"client_port":client_port }
'''
frontend/src/main.js - axios setting
axios.defaults.withCredentials = true;
axios.defaults.baseURL = 'http://192.168.0.150:5000/'; // the FastAPI backend
frontend/view - api call:
<template>
<div>
<p>{{ msg }}</p>
</div>
</template>
<script>
import axios from 'axios';
export default {
name: 'Ping',
data() {
return {
msg: '',
};
},
methods: {
getMessage() {
axios.get('/')
.then((res) => {
this.msg = res.data;
})
.catch((error) => {
console.error(error);
this.msg = error.msg;
});
},
},
created() {
this.getMessage();
},
};
</script>
regardless of how I host the Vue app (with dev server -npm run serve- or after a build with a HTTP server) the message above in the tmeplate shows the ip of the devices on the network from where the page is opened and not the frontend (192.168.0.150:6080) as I would expect.
So that if I set the fastapi middleware to restrict the origins then the API call fails:
allow_origins=["http://192.168.0.150:6080/"]
I also tried to set up a proxy, based on this: https://techformist.com/vuejs-proxy-error-for-backend-connection/ but keep the same behavior.
would you please help with what I miss here?
is my understanding wrong that the API should feel that it is called from the frontend host:port rather than the clients?

Handling endpoints APIs on client side instead of serverMiddleware in Nuxt

I'm on Nuxt 2.15.8 and trying to build an offline app with electron.js and prisma+sqlite for local DB.
In nuxt to hit a local endpoint there is a common way of using serverMiddleware and express like this:
// api.js that will be added to nuxt.config.js file as serverMiddleware
import express from 'express'
const app = express()
app.use(express.json())
export default {
path: '/api',
handler: app
}
which send endpoints beginning with api/ through app handler which I can use to access my BD (the common way to access sqlite3 DB is the same)
// added to api.js
import { PrismaClient } from '../../resources/prisma/client'
const prisma = new PrismaClient()
app.get(`/user/info`, async (req, res) => {
const result = await prisma.user.findUnique({
where: {
id: 1,
},
})
console.console.log(res);
res.json(result)
})
this will work fine on nuxt, also fine on nuxt-electron dev mode. but on built exe file serverMiddleware won't be called. So as it has be done by others (nuxt-electron accessing offline local DB) there must be a way to define endpoints on client side. any idea??
Updated:
as I changed my Nuxt-Electron boilerplate I could access serverMiddleware in exe file but it wont hit the endpoints yet!

Mocking API calls with Detox and Nock

I'm trying to mock API calls from Detox tests and nothing seems to be working. Nock in theory would do exactly what I want but there when I run my tests with nock debugging it isn't seeing any of the requests being made from my app. I'm using axios to make requests and I've tried setting the adapter on my axios instance to the http adapter.
Any suggestions on how to get nock working with Detox or if there is another mocking library you have had success with is appreciated, thanks!
What I ended up doing was leveraging the mocking specified in Detox docs (a separate *.e2e.js file hitting a different endpoint during tests). You define these special files that only run during e2e, I've set mine up to only hit localhost:9091 -- I then run an Express server on that port serving the endpoints I need.
Maybe an ugly way to do it, would love suggestions!
My mock file:
// src/helpers/axios.e2e.js
import axios from 'axios';
const instance = axios.create({
baseURL: `http://localhost:9091/api`,
});
export default instance;
Here's how I am running an express server during tests:
// e2e/mytest.e2e.js
const express = require('express');
let server;
beforeAll(async () => {
const app = express();
app.post('/api/users/register/', (req, res) => {
res.status(400)
res.send({"email": ["Test error: Email is required!"]})
})
await new Promise(function(resolve) {
server = app.listen(9091, "127.0.0.1", function() {
console.log(` Running server on '${JSON.stringify(server.address())}'...`);
resolve();
});
});
})
afterAll(() => {
server.close()
})

Vue.js environment variables not working with axios on Heroku

I have deployed a Vue.js application to heroku an api also hosted on heroku.
The VueJS app uses axios to connect to the api. I have set a config variable in heroku:
VUE_APP_ROOT_API = https://[my-express-api].herokuapp.com/api
Here is my base axios call:
import axios from 'axios'
const token = localStorage.getItem('token')
export default () => {
console.log(process.env.VUE_APP_ROOT_API)
return axios.create({
baseURL: process.env.VUE_APP_ROOT_API,
headers: {
'Content-Type': 'application/json',
token: token,
},
validateStatus: function () {
return true;
}
})
}
However, the console log reveals that the variable is undefined and axios is using the Vue app url as the base for api calls (https://[my-vue-app].herokuapp.com/undefined/) instead of the one specified in the config variable.
Resolved this. It turns out that my config variable was being compiled into the code at build time, so once I deployed to trigger a rebuild, the new config var worked. Adding/Updating config vars will automatically restart the dynos, but that doesn't rebuild any compiled code.
For me, appending the build command in my package.json with '--mode production' before pushing to heroku fixed the issue.
https://forum.vuejs.org/t/production-env-on-app-deployed-in-heroku/71077
Good luck!

Vue application is dropping Axios baseURL

I'm muddling my way through implementing JWT authentication in a new Vue app and am running into an issue. I'm working off of the webpack CLI template FWIW.
In my main.js I have the following code after declaring my Vue app:
window.axios = axios
window.axios.defaults.baseURL = 'https://example.com'
if (localStorage.getItem('token') !== null) {
window.axios.defaults.headers.common['authorization'] = 'Token ' +
localStorage.token
}
Vue.router = router
This works fine when I log in, however after I'm redirected post-login (/sign-up) and then navigate to a new page (/sign-up/inventory) I try the following axios call and get a 404 because the baseURL can no longer be found.
axios.get('myapi/myreport/mydata/').then(function (response) {
console.log(response)
})
.catch(e => {
console.log(e)
})
}
If I log window.axios.defaults.baseURL just prior to the axios call I get an error ("Cannot read property 'defaults' of undefined") so presumably axios isn't even loading? What should I be checking in order to trouble-shoot this?
I moved the axios code up up above my app instantiation on main.js and that seems to have fixed it.