I have created filepond instance in my function which shows modal block with file upload feature. Now I need to destroy created instance on closing modal block, because I have case to call thet function for another uses with new filepond instance and parameters. Please advice how can I realize properly destoy dynamically created filepond instance;
Function initializing filepond:
const showUploader = () => {
const pond = FilePond.create( inputElement, {
acceptedFileTypes: ['image/png', 'image/jpeg', 'image/jpg','application/pdf'],
instantUpload: true,
/* other settings */
server: {
url: '/process.php?' + urlParams,
process: {
onload: (response) => {
console.log(response);
},
onerror: (error) => {
console.log(error);
}
},
revert: {
onload: (response) => console.log(response),
onerror: (response) => console.log(response),
},
load: {
onload: response => { console.log(response); },
onerror: response => { console.log(response); },
}
}
});
}
Function where I have to destroy it:
const closeUploader = () => {
//TODO: Destroy created filepond instance
}
Thanks in advance!
Use the FilePond.destroy method.
<intput type="file" name="filepond" required multiple>
<script>
const inputElement = document.querySelector('input[type="file"]');
// create the FilePond instance
FilePond.create(inputElement);
// destroy the FilePond instance by element reference
FilePond.destroy(inputElement);
</script>
You can also call destroy on the instance itself, in your situation that would be pond.destroy().
https://pqina.nl/filepond/docs/patterns/api/filepond-object/#destroying-a-filepond-instance
Related
Ok these tests were passing a few bit ago. I have made no changes to which version of jasmine I'm using but... can anyone see obvious syntax errors here?
describe("ajax return", function() {
beforeEach(function() {
ajaxSpy = spyOn($, "ajax")
})
describe("on success", function() {
beforeEach(async function() {
ajaxSpy.and.callFake(function(e) {
e.success({"success":true, "remove":{1:"test"},"assign_prestock":"test2"})
})
await catalogDOM.syncAvailability(null)
})
it("should call", function() {
...
})
})
})
When running, I'm getting this error:
1_catalogDOM_spec.js:518 Uncaught (in promise) TypeError: e.success is not a function
UPDATE code for catalogDOM.syncAvailability
catalogDOM.syncAvailability: function(item_name_id) {
return new Promise(function(resolve, reject) {
$.ajax({
type:"POST",
url: "/retrieve-options-availability",
dataType:"json",
contentType:"application/json",
data: JSON.stringify(params)
})
.done(function(response, status_string, jqxhr) {
if (response["success"] == true) {
resolve()
} else {
reject(response["message"])
}
})
.fail(function(jqxhr, error_string, exception_object){
reject("Error loading availability. Refresh & try again or contact us if this persists.")
})
}
Try doing this to debug:
ajaxSpy.and.callFake(function(e) {
// add console.log here !!
console.log('e: ', e);
e.success({"success":true, "remove":{1:"test"},"assign_prestock":"test2"})
})
Apparently, .success is not a function anymore and you can look at the value of e there. I am thinking e is the argument for what's provided in $.ajax(/* e is here */);.
Looking at the documentation here: https://api.jquery.com/jquery.ajax/, I think we need to mock a done function.
Try this:
ajaxSpy.and.callFake(function (e) {
return {
done: function () {
return {
"success":true,
"remove":{1:"test"},
"assign_prestock":"test2",
// edit - create a fail function that's empty here
fail: function() {
// leave empty
}
};
}
};
});
Edit
Instead of doing a spy on ajaxSpy, try spying on catalogDOM directly. Something like this:
spyOn(catalogDOM, 'syncAvailability').and.resolveTo({/* Mock value here */ });
Or
spyOn(catalogDOM, 'syncAvailability').and.returnValue(Promise.resolve({ /* Mock value here */ });
And then you don't have to await it.
How is this possible add new uploader functionality to ckeditor5 like upload audio or video?
I tried for using ckeditor5 doc but it is not clear at all.
I using this vue file for using ckeditor5. in this file, I use a customized uploadadapter for my project, but now I don't know how i can upload another type of file like audio and video in this attitude
<script>
import ClassicEditor from '#ckeditor/ckeditor5-build-classic/build/ckeditor';
import MyUploadAdapter from '../adapter/UploadAdapter';
export default {
data() {
return {
instance: null,
article: {
data: '',
},
}
},
mounted() {
this.initialize();
},
methods: {
// Initializing Editor
initialize: function () {
ClassicEditor
.create(document.querySelector("#editor"), this.config)
.then(editor => {
// get initial instance object of editor
this.instance = editor;
// set initial binder of editor on start
editor.model.document.on('change', () => {
this.valueBinder(editor.getData())
});
editor.plugins.get('FileDialogButtonView')
// This place loads the adapter.
editor.plugins.get('FileRepository').createUploadAdapter = (loader, article) => {
return new MyUploadAdapter(loader, this.article);
}
})
.catch(error => {
console.error(error);
});
},
}
},
}
</script>
For Upload file you can use CKFinder.
For the configuration of CKfinder, Please refer this link.
ClassicEditor
.create( editorElement, {
ckfinder: {
uploadUrl: '/ckfinder/core/connector/php/connector.php?command=QuickUpload&type=Files&responseType=json' // here you can set your own file path
}
} )
.then( ... )
.catch( ... );
I'm trying to learn VueJS and it's going well but i run into one problem where i can't get multiple components to work on one page, for some reason the html will load but everything in my export default wont work.
So i have 2 components: a ShortenerComponent and a StatsComponent the ShortenerComponent works and does everything it should, but the StatsComponent will only load the html and will not do anything inside the export default this is my code:
StatsComponent.vue (the ShortenerComponent is the same except for the methods and html.):
<script>
// get the csrf token from the meta
var csrf_token = $('meta[name="csrf-token"]').attr('content');
export default {
data() {
return {
};
},
test() {
this.getStats();
},
methods: {
// get all the existing urls
getStats() {
console.log('console log something');
axios.get('urls').then((response) => {
console.log('console log something');
});
},
}
}
My shortenercomponent:
<script>
// get the csrf token from the meta
var csrf_token = $('meta[name="csrf-token"]').attr('content');
export default {
data() {
return {
shortUrl: '',
url: '',
error: '',
};
},
methods: {
createUrl() {
axios({
method: 'post',
url: '/',
data: {
_token: csrf_token,
url: this.url
},
}).then(response => {
console.log(response);
this.shortUrl = response.data.hash;
}).catch(error => {
this.error = error.response.data.message;
});
}
}
}
and last but not least my app.js file
Vue.component('shortener',require('./components/ShortenerComponent.vue'));
Vue.component('stats', require('./components/StatsComponent.vue'));
var vue = new Vue({
el: '#app',
});
I hope someone could figure out what i did wrong :D
So in my code i had the test method, i thought that would call the getStats method. What i did not now is that Vue has the created method used to run code after an instance is created.
So what i had to do was:
function created()
{
this.getStats();
}
Source: Vue instance Lifecycle Hooks
Here's the code I would like to test. Specifically, I want to spy on a utility called Linkvalidation.validate to make sure that it is called when handleSave() is called.
This code lives in a component called the CondensedFormModal:
handleSave() {
LinkValidation.validate(this.state.url)
.then((response) => {
if (response.success) {
this.setState({
message: ''
});
}
})
.fail((error) => {
if (error && error.message && error.message.match(/invalid internal link/)) {
this.setState({
message: 'The URL is an internal link. Please use a public link.'
});
} else {
this.setState({
message: 'The URL is invalid.'
});
}
});
Here is the LinkValidation.validate utility I'm using in the handleSave function above:
define([
'module/api-call'
], function(
ApiCall
) {
'use strict';
// Calls validation API
function validate(link) {
var deferred = $.Deferred();
ApiCall.apiCall(
'/url/check',
{ link: link },
'POST',
function(data) {
if (data.success === true) {
deferred.resolve(data);
} else {
// This link is not valid
deferred.reject(data);
}
},
function() {
deferred.reject();
}
);
return deferred;
}
return {
validate: validate
};
});
Here is my test file--
Import statement:
import { validate } from 'modules/link-validation.js';
Test:
describe('when the URL is an internal link', () => {
it('displays a unique error message', (done) => {
let modal = shallowInstance(<CondensedFormModal />);
modal.setState({
url: 'https://internal.example.com'
});
let x = jasmine.createSpy('validate').and.returnValue({
message: "invalid internal link",
success: false,
url: 'https://example.com'
});
modal.handleSave();
_.defer(() => {
expect(x).toHaveBeenCalled();
done();
});
});
});
When I run this test, it consistently fails with the message "Expected spy validate to have been called."
After looking at the Jasmine docs (https://jasmine.github.io/2.1/introduction) and various other Stack Overflow questions (Unit test with spy is failing. Says spy was never called , Jasmine test case error 'Spy to have been called' , etc.) I'm unable to make this work. I've also tried callFake and callThrough instead of returnValue.
Any ideas on how to spy on LinkValidation.validate to assure that it was called?
This line:
let x = jasmine.createSpy('validate')
creates new spy function (it doesn't spy on existing validate function) and handleSave function is not aware of it. So it's not called at all.
You have to set spy on function that is actually called in your component. Since your CondensedFormModal uses LinkValidation module (which I assume is imported in component file) you have to set spy on validate function from imported module which is actually used by component. So I'd suggest something like this:
In CondensedFormModal constructor set LinkValidation as component property to make it easily accessible in tests:
this.LinkValidation = LinkValidation;
In handleSave use validate function like this:
this.LinkValidation.validate(this.state.url);
And finally in test set spy on component validate method:
describe('when the URL is an internal link', () => {
it('displays a unique error message', (done) => {
let modal = shallowInstance(<CondensedFormModal />);
...
spyOn(modal.LinkValidation, 'validate').and.returnValue({
message: "invalid internal link",
success: false,
url: 'https://dash.vagrant.local.rf29.net/shopping/new'
});
modal.handleSave();
_.defer(() => {
expect(modal.LinkValidation.validate).toHaveBeenCalled();
done();
});
});
});
I built an app on Laravel 5.3 using vue.js and im starting to move over to vue.js to make the pages dynamic. I got everything working on a single page so want to convert that over to a component but after doing so I get the following error:
[Vue warn]: Error when rendering component <homepage> at C:\xampp\htdocs\.......
TypeError: Cannot read property 'nxt_weekly' of undefined
I was passing data to the view like so:
const app = new Vue({
el: '#app',
mounted: function () {
this.fetchEvents();
},
data: {
loading: true,
stats: []
},
methods: {
fetchEvents: function () {
this.$http.get('home/data').then(function (response) {
this.stats = response.body;
this.loading = false;
}, function (error) {
console.log(error);
});
}
});
In stats[] is where I hold the JSON response from the API and then call them all in my view like so:
<span class="stat" v-text="'stats.nxt_today'"></span>
....
....
This works but when I switch over to creating a component the errors listed above show, my new code is:
Vue.component('homepage', require('./components/Homepage.vue'),{
mounted: function () {
this.fetchEvents();
},
data: function () {
return{
loading: true,
stats: []
}
},
methods: {
fetchEvents: function () {
console.log('running here');
this.$http.get('home/data').then(function (response) {
this.stats = response.body;
this.loading = false;
}, function (error) {
console.log(error);
});
}
}
});
What am I doing wrong? How come my stats[] object is now empty when the component is trying to access it?
You need to pass your stats as a property to the component using v-bind, as shown below:
<homepage v-bind:stats="stats"></homepage>
The above needs to be done in your root template. And in your homepage component, you can receive the value in props as follows:
Vue.component('homepage', {
props: ["stats"],
mounted: function () {
// ...
},
// ...
}
Within the template of this component, you will be able to access stats.nxt_today normally.
By the way, is your stats an array or an object? You have defined it as an empty array initially, but accessing it as an object.
If you still have issues, you can use vue-devtools to view all the objects available within a component.