Can't use vue.js from django - django

I introduced vuejs using webpack in django, but I can not use vue instances from django templates.
Looking at the chrome devtool, the transpiled js is loaded correctly, but shows {{message}}.
The following message is output on the console of chrome devtool.
TypeError: undefined is not an object (evaluating 'hasOwnProperty.call (it, key)')
ReferenceError: Can't find variable: Vue
This is my code.
main.js
import Vue from 'vue'
import App from './App.vue'
import vuetify from '#/plugins/vuetify' // path to vuetify export
window.Vue = require('vue');
Vue.config.productionTip = false
new Vue({
render: h => h(App),
vuetify,
}).$mount('#app')
html
{% load render_bundle from webpack_loader %}
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Example</title>
</head>
<body>
{% verbatim %}
<div id="app">
{{ message }}
</div>
{% endverbatim %}
{% render_bundle 'main' %}
<script>
var app = new Vue({
el: '#app',
data: {
message: 'Hello Vue!'
}
})
</script>
</body>
</html>
log(django)
django | [09/Jan/2020 11:22:58] "GET /vue/ HTTP/1.1" 200 374
django | [09/Jan/2020 11:22:58] "GET /static/webpack_bundles/main-ccb1054f18bba9ee992d.js HTTP/1.1" 304 0
urls.py
from django.urls import path
from .views import signupfunc, loginfunc, listfunc, logoutfunc, vuefunc
urlpatterns = [
path('signup/', signupfunc, name='signup'),
path('login/', loginfunc, name='login'),
path('list/', listfunc, name='list'),
path('logout/', logoutfunc, name='logout'),
path('vue/', vuefunc, name='vue'),
]
vies.py
<snip>
def vuefunc(request):
return render(request, 'vue.html')

This might be a dumb question, but are you importing your main.js file from your template? It would look something like this:
<script src="{% static 'js/main.js' %}"></script>
Also, just as an aside, I use Vue with django and always list my own delimiter in the Vue code so I don't have to put {% verbatim %} tags around every variable. It looks something like this:
var app = new Vue({
el: '#app',
delimiters: ['${', '}'],
data: {
message: 'Hello Vue!'
}
})
and you can obviously pick whichever delimiters you want.

Related

Django Templates with Vue

I'm trying to integrate vue-components into django-templates. The basic setup did work, but I'm stacked with a component which needs an import itself.
Here is the component (vue/dropdown.html):
<div id="app">
<template>
...
</template>
</div>
<script setup>
import { computed, ref } from 'vue'
import {CheckIcon, ChevronUpDownIcon} from '#heroicons/vue/20/solid'
const query =ref('')
const selectedPerson = ref(null)
...
var app = new Vue({
delimiters: ['[[', ']]'],
el: '#app',
data: {
message: 'Hello Vue!',
},
});
</script>
So, the 2 imports:
import {computed, ref} from Vue
import {CheckIcon, ChevronUpDownIcon} from '#heroicons/vue/20/solid'
are triggering the error in the browser's console:
Cannot use import statement outside a module
What is the proper way to use the imports?
I'm calling the dropdown.html from base.html:
<html lang="{{ LANGUAGE_CODE }}">
<head>...</head>
<body>
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
{% include 'vue/dropdown.html' %}
</body>
</html>
I think this happens because vue cdn should be imported into dropdown.html.Please try this fix and let me know if it works.
Thank you

How to render Vue with Django

I'm working on a small application using Vue.js and Django on Digitalocean, so I have installed Django Webpack loader and the tracker also, now I have executed my Django server and my vue.js also using npm run serve and when I access to my webpage localhost:8000 I see only a blank page since everything is installed correctly, This is my HTML page ( when I inspect on chrome browser )
<html>
<head>
<title>Title of the document</title>
</head>
<body>
<div id="app"></div>
<script type="text/javascript" src="http://0.0.0.0:8080/js/app.js"></script>
</body>
</html>
PS : i think the problem is in app.js ( because i follow the link and i get an error )
This site can’t be reachedThe webpage at http://0.0.0.0:8080/js/app.js might be temporarily down or it may have moved permanently to a new web address.
ERR_ADDRESS_INVALID
you should config your vue application first creating vue.config.js file.
vue.config.js:
const BundleTracker = require("webpack-bundle-tracker");
module.exports = {
// on Windows you might want to set publicPath: "http://127.0.0.1:8080/"
publicPath: "http://0.0.0.0:8080/",
outputDir: "./dist/",
chainWebpack: (config) => {
config
.plugin("BundleTracker")
.use(BundleTracker, [{ filename: "./webpack-stats.json" }]);
config.output.filename("bundle.js");
config.optimization.splitChunks(false);
config.resolve.alias.set("__STATIC__", "static");
config.devServer
// the first 3 lines of the following code have been added to the configuration
.public("http://127.0.0.1:8080")
.host("127.0.0.1")
.port(8080)
.hotOnly(true)
.watchOptions({ poll: 1000 })
.https(false)
.disableHostCheck(true)
.headers({ "Access-Control-Allow-Origin": ["*"] });
}
// uncomment before executing 'npm run build'
// css: {
// extract: {
// filename: 'bundle.css',
// chunkFilename: 'bundle.css',
// },
// }
};
Then load render_bundle from webpack_loader. Your django template will be like:
{% load render_bundle from webpack_loader %}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Document</title>
</head>
<body>
<!-- This part is in the screenshot at the bottom! -->
<h1>Vue JS</h1>
<div id="app"></div>
{% render_bundle 'app' %}
</body>
</html>
Make Sure you are using webpack-bundle-tracker of version #0.4.3
You can follow this link for step by step tutorial.

usinig Django urls in react, is_authenticated in react, displaying context in react

So, I've got 3 questions
How to use Django's URLs in react
EXAMPLE:
index.js (in react)
<Router>
<div>
<nav className="navbar navbar-inverse bg-inverse">
<div className="container">
<Link to="/" className="navbar-brand">PetFinder</Link>
<Link to="/storage" className="navbar-brand">Storage </Link>
Sign-Up <== like this
</div>
</nav>
<Route exact path={"/"} component={PetRegistration} />
<Route path={"/storage"} render={() => <Storage ids={checkingName} />} />
</div>
</Router>
urls.py
urlpatterns = [
path('admin/', admin.site.urls),
#path('api-auth/', include('rest_framework.urls', namespace="rest_framework")),
path('api/animals/', include('petsite.urls', namespace='petsite')),
path('api/user_info', core_views.UserInfo.as_view()),
path('signup/', core_views.signup, name='signup'),
path('', csrf_exempt(core_views.index), name='index'),
path(r'^login/$', auth_views.login, name='login'),
]
is_authenticated in react
How I did it:
In index.html
I wrote this ******. I am ashamed of this. Don't judge me, okay just a bit...
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
<meta name="theme-color" content="#000000">
<!--
manifest.json provides metadata used when your web app is added to the
homescreen on Android. See https://developers.google.com/web/fundamentals/engage-and-retain/web-app-manifest/
-->
<link rel="manifest" href="%PUBLIC_URL%/manifest.json">
<link rel="shortcut icon" href="%PUBLIC_URL%/favicon.ico">
<!--
Notice the use of %PUBLIC_URL% in the tags above.
It will be replaced with the URL of the `public` folder during the build.
Only files inside the `public` folder can be referenced from the HTML.
Unlike "/favicon.ico" or "favicon.ico", "%PUBLIC_URL%/favicon.ico" will
work correctly both with client-side routing and a non-root public URL.
Learn how to configure a non-root public URL by running `npm run build`.
-->
<title>React App</title>
</head>
<body>
<noscript>
You need to enable JavaScript to run this app.
</noscript>
<div class="signUpBlock">
Sign-Up
</div>
<div id="root">
</div>
<span class="currentUser" style="display: none">{{user.id}}</span>
<span class="currentUserName" style="display: none">{{user.username}}</span>
<span id="DJANGO_USER" style="display: none"></span>
<!--
This HTML file is a template.
If you open it directly in the browser, you will see an empty page.
You can add webfonts, meta tags, or analytics to this file.
The build step will place the bundled scripts into the <body> tag.
To begin the development, run `npm start` or `yarn start`.
To create a production bundle, use `npm run build` or `yarn build`.
-->
<script type="text/javascript">
var WHETHER_DJANGO_USER_IS_AUTH = "{{user.is_authenticated|yesno:"true,false"}}";
document.getElementById("DJANGO_USER").innerHTML = WHETHER_DJANGO_USER_IS_AUTH;
</script>
</body>
</html>
Check the code below:
<script type="text/javascript">
var WHETHER_DJANGO_USER_IS_AUTH = "{{user.is_authenticated|yesno:"true,false"}}";
document.getElementById("DJANGO_USER").innerHTML = WHETHER_DJANGO_USER_IS_AUTH;
</script>
<span id="DJANGO_USER" style="display: none"></span>
AND THEN IN index.js I do this
let boolButString = $('#DJANGO_USER').text()
var StringToBool = (boolButString === 'true');
If StringToBool = true I do smth (means that user is logged in)
else StringToBool != true I do smth (means that user is not logged in)
if (StringToBool) {
do smth
} else {
make some tea for him
}
I don't think I did it in a right way can you suggest me smth?
Is it real to check whether a user is auth. or not?
How to display Django context in react.
You might have seen how I did it in index.html
As usual, I wrote:
def index(request):
return render(request, 'index.html', {
"user" : request.user,
})
end then
<span class="currentUser" style="display: none">{{user.id}}</span>
grab data through jquery and display it in react app.
What can you suggest me?
How to display context properly?
Sry for cups.

django webpack loader setting to load css

It works when I set up like below. I am using django-webpack-loader
index.html
{% load render_bundle from webpack_loader %}
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Jayground</title>
{% render_bundle 'main' 'css' %}
</head>
<body>
<div id="react-app"></div>
{% render_bundle 'main' 'js' %}
</body>
</html>
Header.js
import styles from './header.css';
export default class Header extends React.Component {
render(){
<div className="header">
hello
</div>
}
}
webpack.config.js (I made styles.css separately and then load css file in html separately so that className="header" works.)
config.plugins = config.plugins.concat([
new ExtractTextPlugin('styles.css'),
]);
config.module.rules.push(
{
test: /\.css$/,
use: ExtractTextPlugin.extract({
use: 'css-loader'
})
}
)
According to what I understood, code below should work too. If I don't separate css file by using ExtractTextWebpackPlugin, bundle js file have css information in it like this.
exports.push([module.i, ".header {\r\n background-color: blue;\r\n}\r\n\r\n.extra {\r\n\tfont-size: 50;\r\n}", ""]);
css should be loaded properly.
Header.js
import styles from './header.css';
export default class Header extends React.Component {
render(){
<div className={styles.header}>
hello
</div>
}
}
webpack.config.js
config.module.rules.push(
{
test: /\.css$/,
use: ['style-loader', 'css-loader']
}
)
Do I miss something to work properly?

Dynamic programing in django not working properly

In django, tried to create a dynamic web page with ajax. But it doesn't takes the automatic reload. The requesting to the server is only done when reloading the page. Here my codes.
How i make into dynamic reloading.
Views.py
from django.shortcuts import render
from django.http import HttpResponse
from random import randrange
def main(request):
return render(request, 'index.html')
def random_generator(request):
return HttpResponse(randrange(0, 100))
urls.py
from django.conf.urls import patterns, include, url
from django.conf import settings
from django.conf.urls.static import static
urlpatterns = patterns('',
url('^main/$', 'Signup.views.main'),
url('^random/$', 'Signup.views.random_generator')
)
random.html
<!DOCTYPE html>
<html>
<head>
<script type="text/javascript">
function refreshRandom() {
$.ajax({
url: '/random/',
dataType: 'html',
success: function(data) {
$('#random').html(data);
},
complete: function() {
window.setTimeout(refreshRandom, 1000);
}
});
}
window.setTimeout(refreshRandom, 1000);
</script>
</head>
<body>
<div id='random'></div>
</body>
</html>
You can use Jquery like this
$(document).ready(function() {
// JQuery code to be added in here.
});
in your template use
<script src="{% static "/js/jquery.js" %}"></script>
<script src="{% static "/js/rango-ajax.js" %}"></script>