how to access vue.js api key in laravel application - laravel

hello there i am trying to access my youtube api key located in the .env file from within this code:
<template>
<div class="YoutubeDash__wrapper">
<video-group :videos="videos"></video-group>
</div>
</template>
<script>
import VideoGroup from './VideoGroup.vue';
import Search from './Search';
export default {
components: {
VideoGroup
},
created(){
Search({
apiKey: process.env.VUE_APP_SECRET,
term: 'laravel repo'
}, response => this.videos = response);
},
data(){
return {
videos: null
}
}
}
</script>
According to the documentation using env variables with vue.js. Everything seems to be correct. In my .env file i say: VUE_APP_SECRET=xxxxxxxxxxxxxxx, what am i missing here ?
I get this error message:
app.js:37809 Error: YouTube search would require a key
Any tips are welcome! Thanks a lot!

We need to work with a small amount of information here so I am going to make a few assumptions (based on the tags) mostly that you are using laravel and laravel-mix to compile your resources.
For laravel(-mix) to make your .env variables accessible by JS you need to prefix them with MIX_ i.e. MIX_VUE_APP_SECRET. This will make your variable accessible as process.env.MIX_VUE_APP_SECRET.

I prefer excluding laravel-mix from this process.
Usually, in my blade entry-point I use meta tags:
<meta name="myVal" content="{{ config('<any-config-key>') }}">
<any-config-key> can be any laravel configuration key including those taken from .env.
Then, in my javascript I do something like:
const setVueGlobal = (metaHeaderName, vueGlobalName) => {
let value = document.head.querySelector('meta[name="' + metaHeaderName + '"]').content;
if (!value) {
console.error('some error msg');
return null;
}
Vue.prototype[vueGlobalName] = value;
return value;
};
setVueGlobal('myVal', '$myVal');
Finally, accessing using this.$myVal

Related

How to show README.md in a web page in Laravel?

I hava a laravel project, there is a README.md in the root directory. I can see the render result after pushing to GitHub, but I want to render markdown document in the local development browser.
I am trying two ways:
Read file from markdown file
convert markdown file to html with something like Webpack
Who can give a demo for this?
Since the mail blade templates parse markdown, you can use a similar approach to layout.blade.php which uses Illuminate\Mail\Markdown::parse.
In your template, such as welcome.blade.php, add this:
{{ Illuminate\Mail\Markdown::parse(file_get_contents(base_path() . '/README.md')) }}
Here is a Laravel Mix / Webpack solution, convert markdown file to html, and required in Vue.js, then show it with v-html.
First add markdown-loader
yarn add markdown-loader html-loader
Add config in webpack.mix.js, Laravel Mix can add custom config of Webpack.
mix.webpackConfig({
module: {
rules: [{
test: /\.md$/,
use: ["html-loader", "markdown-loader"],
}]
}
});
Considering README.md is in the root of Project, add a alias in webpack.mix.js
mix.alias({
'#': '/resources/js',
'#root': '/',
});
Now we can use a vue component to show the README.md at the root directory.
<script>
const readme = require('#root/README.md')
export default {
data() {
return {
readme: ""
}
},
created() {
this.readme = readme
}
}
</script>
<template>
<div class="container" ref="container" v-html="readme" />
</template>

Laravel mix removes subfolder from image path

I've set up an alias for my public folder where I've placed my images.
So they are inside public/images. I have a subfolder for certain types of images - in this case, card brands.
They're in public/images/card-brands
Here is my alias config:
mix.webpackConfig({
resolve: {
extensions: ['.js', '.vue', '.json'],
alias: {
'#': __dirname + '/resources/js',
'#public' : __dirname + '/public'
},
},
})
I'm importing the images in my vue component file:
import amex from '#public/images/card-brands/amex.svg'
import discover from '#public/images/card-brands/discover.svg'
import visa from '#public/images/card-brands/visa.svg'
import mastercard from '#public/images/card-brands/mastercard.svg'
Then using it inside my components data like so:
export default {
name: 'PaymentMethod',
data() {
return {
...
visaSvg: visa,
mastercardSvg: mastercard,
discoverSvg: discover,
amexSvg: amex,
currentCardBrand: this.initialCurrentCardBrand
...
}
},
props: {
...
initialCurrentCardBrand: String,
...
}
computed: {
getCurrentCardBrandSvg() {
switch (this.currentCardBrand) {
case 'mastercard':
return this.mastercardSvg;
break;
case 'visa':
return this.visaSvg;
break;
case 'amex':
return this.amexSvg;
break;
case 'discover':
return this.discoverSvg;
break;
}
}
}
...
Finally, I'm using it on my template as and image src: <img class="w-10" :src="getCurrentCardBrandSvg">
Now, even though the images and my import path are using the card-brands subfolder, the URL that is generated ignores this and just looks for the images in the root images folder.
It should be:
/public/images/card-brands/visa.svg
but it's generating as
/public/images/visa.svg
How can I get it to keep my subfolder?
try this instead {{ asset('/images/card-brands/mastercard.svg')) }}
I faced a similar issue in laravel. I used the above format.Please correct me if Im wrong.
Edit: This could be slightly wrong. It works correctly for importing images via javascript, but I think grabbing images via laravel in blade templates still needs the images in the public folder.
The issue was not knowing that I was supposed to put my images folder inside the resources folder rather than public.
Laravel Mix will compile the images like it does the JS and SCSS and place it in public automatically.
So I created an images folder in resources, deleted my manually made images folder in public, and made an alias:
alias: {
'#images': __dirname + '/resources/images'
}
and now I can link to that inside my vue component.
import amex from '#images/card-brands/amex.svg'
import discover from '#images/card-brands/discover.svg'
import visa from '#images/card-brands/visa.svg'
import mastercard from '#images/card-brands/mastercard.svg'
The generated images will automatically be placed in public on the root level once I run npm run dev or npm run prod

How to load csv files into a nuxt vue component

I am currently trying to load a csv file into a Nuxt page. The folder structure is below and produces the error "Failed to load resource: the server responded with a status of 404 (Not Found)":
Project
|
+--pages
|
+--lesson
|
+--index.vue
+--file.csv
import * as d3 from 'd3';
export default{
data(){
return{
dataset1:[]
}
mounted(){
d3.csv('file.csv', (myData) => {
console.log('Mydta', myData);
this.dataset1 = myData;
})
}
}
I have added the following to the web pack config in the nuxt-folder:
build: {
/*
** You can extend webpack config here
*/
extend(config, ctx) {
config = {
module: {
rules: [
{
test: /\.csv$/,
loader: 'csv-loader',
options: {
dynamicTyping: true,
header: true,
skipEmptyLines: true
}
}
]
}
}
}
}
Thanks in advance
I recently had the same question and ended up using the #nuxt/content module – worked like a charm, didn't even need to include d3 (which is usually my go-to for parsing CSV files).
I believe the issue is you cannot access the csv file the way you are attempting to, the way to do that would be storing the file in the '/assets' directory which you can then access as shown in the docs I linked ~/assets/file.csv I think this is also a more correct location for storing such files to avoid having lingering files throughout the project
This worked for me:
async mounted() {
const d = await d3.csv("/data.csv");
console.log(d);
}
With data.csv placed in public folder.

Laravel environment variable with React: is this a good practice?

I have a React app which makes API requests to a Laravel backend.
My app is hosted on Heroku (I do not know if it changes something for my question).
I would like to differentiate a production and a local environment for these requests. I do it as follows.
In my "welcome.blade.php", I add this meta tag:
<meta name="app_env" content="<?php echo env("APP_ENV") ?>" />
The APP_ENV contains either "production" or "local".
In my React app, I have this script:
export let urlApi = (document.querySelector("[name=app_env]").content === "production" ) ?
"https://laravel-react.herokuapp.com/api"
:
"http://localhost/laravel_react/public/api"
;
And I import this function in each component which needs it:
import { urlApi } from './../findUrlApi';
// .....
return fetch(`${urlApi}/products`,{
headers: {
"Content-Type": "application/json",
"Authorization": "Bearer "+localStorage.getItem("token")
}
})
It works fine.
But my question is, is it a good practice? (I am a beginner in React).
I don't think that it is a good practice. Environment variables (like APP_ENV and API URLs) should not reside in the source code.
However, you could store them like usual in Laravel .env file but by prefixing the key with MIX_. For example: MIX_API_URL=http://localhost. Every MIX_* variables in .env file will be exposed to your React application. Then, you could get MIX_API_URL value from your React application by calling process.env.MIX_API_URL.
Updated Laravel .env file
...
MIX_APP_ENV=production (or local) # Should be same as APP_ENV
MIX_API_LOCAL_URL=http://localhost/laravel_react/public/api
MIX_API_PRODUCTION_URL=https://laravel-react.herokuapp.com/api
In React components that need it
const { MIX_APP_ENV, MIX_API_LOCAL_URL, MIX_API_PRODUCTION_URL } = process.env;
const apiUrl = MIX_APP_ENV === 'local'? MIX_API_LOCAL_URL: MIX_API_PRODUCTION_URL;
return fetch(apiUrl + '/products', { ... });
If calling process.env.MIX_API_URL does not work and you are running npm run watch, try restarting npm run watch and hard reload your browser.
Reference
Laravel Documentation - Compiling Assets (Mix) - Environment
Variables

i18n wants to load an unspecified translation

I'm currently working on an Aurelia project (web framework like Angular2).
I followed the guide on their github account but encountered a problem.
First, the browser returned me this error:
GET http://localhost:9000/src/locale/nl/translation.json?_=1450946571510 404 (Not Found)
Secondly, I'm using two languages in my application: Dutch (nl-BE) and French (fr-BE).
Here is how my folder structure looks like:
src (inside root)
.. locale
..... fr-BE
........ translation.json
..... nl-BE
........ translation.json
Here is what my full main.js file looks like:
import 'bootstrap';
import {I18N} from 'aurelia-i18n';
export function configure(aurelia) {
aurelia.use
.standardConfiguration()
.developmentLogging()
.globalResources('converters/dateFormat')
.plugin('components/index')
.plugin('plugins/index')
.plugin('aurelia-i18n', (instance) => {
instance.setup({
resGetPath: 'src/locale/__lng__/__ns__.json',
lng: 'nl-BE',
attributes: ['t', 'i18n'],
getAsync: true,
sendMissing: false,
fallbackLng: 'fr-BE',
debug: false
});
});
aurelia.start().then(a => a.setRoot());
}
I'm trying to setup a hello world where I have my view and viewmodel set like this:
import {inject} from 'aurelia-framework';
import {I18N} from 'aurelia-i18n';
#inject(I18N)
export class EntryDetails {
constructor(i18n){
this.i18n = i18n;
this.i18n.setLocale('nl-BE').then(() => console.log('test'));
}
}
And my view:
<template>
<span t="hello"></span> <span t="world"></span>
</template>
The problem is not that it's not working. The problem is that I'm getting an error that states my folder nl is missing in my locale folder. But I never specified that anywhere..
That is how i18next resolves translation files.
The lookup order for keys is always:
nl-BE language + country
nl language only
fallback thats defined in options.fallbackLng (en) (string or array of fallback language)
loaded resources:
locale/en/translation.json
locale/nl/translation.json
locale/nl-BE/translation.json
http://i18next.com/translate/#resolve
So you need to have nl/translation.json, even if it is not specified in config. It can be just empty but valid json file with content {}

Resources