I'm trying to get an access to datapoints in new cumulocity version. In older version such things as c8yDataPointSvc and schemaPropertiesSvc. I can't seem to find them anywhere. Basically I need components to work with datapoint as in the picture below. I would appreciate any info on how to either reuse those old components or a new way of using them as there is such.
Thanks a lot!
I see here three options. First what I am going to say is that we in Cumulocity use a hybrid approach for our core applications, since we have a lot of functionalities still written in AngularJS. Same as the one that you need. There is no equivalent in Angular yet. That is why you have several options to use those old services.
One is in a hybrid application to you a bridge service where you can define the upgraded c8yDataPointSvc like that -
constructor(
private ng1Injector: any,
...
) {}
get ng1DataPointSvc() {
return this.ng1Injector.get('c8yDataPointSvc');
}
This ng1Injector is a constructor input variable that we define when we provide that bridge service in the upgrade module like this:
{
provide: BridgeService,
useFactory: BridgeFactory,
deps: ['$injector', ...]
}
This way you will still have an Angular application, you will still use the provided from us factory c8yDataPointSvc in your Angular application just by upgrading it using anguar hybrid app upgrade functionality.
Other option is to just keep your widget an AngularJS one and when you have a hybrid app, you can just import the AngularJS widget and the angular compiler will take care of the upgrade/downgrade. This is what we are doing with a lot of our customers, who have angulatJS widgets and are using Cumulocity versions above 10.5.0.*
And the last option will be to not use the AngularJS services you need and using our SDK just implement the functionalities used from c8yDataPointSvc. But that will be the biggest effort probably.
Related
First, I'd like to explain that I have a Vue component repository that is responsible for displaying data retrieved from an http service. Rather than the component itself managing the same data retrieval per instance and spamming the client with network requests, I've managed to find a solution which allows another component to be mounted to the root directly (which I've dubbed as a "Service" due to its similarity to Angular) to manage the data those components need instead. This works great and other components can access it via Vue.prototype (via this.$TestService.value). It has some caveats but for the most part it accomplishes exactly what I needed. This may be uncommon, but those that use Vuex are using a similar methodology and I don't want to use the store paradigm.
I've made a very simple Vue JsFiddle to show this in action...
https://jsfiddle.net/spronkets/8v31tcfd/18
Now, to the point... I'm using #testing-library/vue, #vue/test-utils, and Jest to test the components and get test coverage and now I get errors anytime I run the tests due to the service not existing on the Vue.prototype during the test execution. I don't want to mock out the functionality of the "Service" layer, so does anyone have a solution to test these root-mounted components? I've tried manually exporting the services (unmounted and mounted) and including them in the mock section as well as importing the files directly into the test files but the "Service" is always undefined when the component is trying to retrieve the value and ONLY during test execution...
I've also created a simple repository modelled after the Vue component repository I am working with below...
https://github.com/kcrossman/VueServiceExample
To get started, clone the repo and follow the README.md included in the repo. Thanks!
I would go against using the real service if it is asyncronous, but if you just want to register it to be available you can follow the mock instructions but instead of mocking with an object just import the real service. Although after seeing your TestService implementation you will need to separate the real service from the service registration and export it to be able to register it in local vue.
You need to create and prepare your custom Vue instance in your tests in order to use any custom functionalities in your unit tests (like stores, routers, and anything else). (You can use your real modules with the custom instance, don't have to mock anything.)
In your case you should create a new Vue instance with "createLocalVue" function from '#vue/test-utils' and apply your custom prototype functionalities on that. After that you can write proper test cases accessing that custom features as well.
Update:
For those that might be referring to this in the future, Vue Plugins might be a better solution for this kind of functionality.
I stumbled along this issue in GitHub and that led me to the fix I made below:
https://github.com/testing-library/vue-testing-library/issues/113
Specifically, this comment by user nikravi:
ok, I found the fix. The trick was to add
import Vue from "vue";
import Vuetify from "vuetify";
Vue.use(Vuetify);
and then the render() works without warnings.
After I manually imported Vue and set Vue.prototype.$TestService = TestService directly in the unit test, it got passed that error. Personally, I think this is pretty silly, but it worked.
After this worked, I also found that you can access the Vue instance directly within the render callback (from #testing-library/vue), so I finished on this code instead of importing Vue:
render(TestComponent, {}, vue => {
vue.prototype.$TestService = TestService;
});
I've included all the commits to solve my issue in the repo I posted previously:
https://github.com/kcrossman/VueServiceExample
Some of the tests were malformed but once I made those changes, the tests started to work and I updated some other files to be a bit nicer for people to refer to.
Anyone already used https://reimagined.github.io/resolve/ and got hot reload for react working?
Cheers
-raf
TL;DR
This small DIFF (3 files) for the HackerNews example application illustrates how to implement the simplest HMR:
* On Diffy: https://diffy.org/diff/kgfz1h97zr9sisxcfkb0m5cdi
* Permalink: https://pastebin.com/hv87aquw
hacker-news/client/hmr.js
hacker-news/client/index.js
hacker-news/config.app.js
Complete answer:
Although the reSolve framework’s examples mostly use React, it is up to you how you implement the frontend, so you can implement custom logic to support hot reloading.
Also, note that the reSolve framework supports automatic rebuilding of server bundles and custom client sources specified in the application config as in the following code sample:
https://github.com/reimagined/resolve/blob/master/examples/hacker-news/config.app.js#L49-L67
So, you can take one of the following two approaches to implement hot reloading in your reSolve-based application:
1) Implement an SSR renderer for your application, like in this example: https://github.com/reimagined/resolve/blob/master/examples/hacker-news/client/ssr.js. You can even use a simplified version of this file containing only imports - it will suffice for the task. The main point is that this SSR renderer is rebuilt automatically after any of UI source files is changed, which you can use as an indication of file changes. On the client side, you can send long-polling requests to this handler and invoke page reloading on a change.
2) Generate a fully custom frontend using a builder that provides hot reloading out-of-the-box (for example, create-react-app), and link that frontend to your reSolve application as in the following example:
https://github.com/reimagined/resolve/tree/master/examples/with-vanillajs
I’m new to vue.js. I have a requirement to develop a calendar with a scheduling feature for a Classic ASP project. I did some research and found the following project on GitHub which is developed using vue.js.
https://github.com/ClickerMonkey/dayspan-vuetify
I can use this project to implement the feature as a separate application. But I need to plug this inside to classic ASP project since there is no API to develop separately.
I was spending a lot of time to find how to make that possible but couldn't find an easy guide. Any help would be greatly appreciated. Thanks.
Using Vue#Next(AKA v3) you can instantiate separate Vue apps on the client.
Simply include the vue3.js client file, extract the desired methods from Vue,
create the app with its configuration and mount it to the desired DOM element.
You'll need to support interfacing, likely when the component is "mounted", between the app and third party object like a calendar scheduler class, cookie class, localStorage whatever you want to support. You can even communicate between app if you set up handles between them. Vue 3 also has providers and injectors which let you affect state and methodology at a parent level and inject it at child levels without the need to pass through each child level.
It's great for learning, rapid development, prototyping, small test components, trial and error type work, but it's a step or few away from typical Vue development paradigm.
FYI, Vue3 also supports dynamic asynchronous components.
<script src="/dist/vue.global.js"></script>
const { createApp, defineAsyncComponent } = Vue;
const app1 = createApp({first app configuration object});
const app2 = createApp({second app configuration object});
const vmApp1 = app.mount( app1 selector );
const vmApp2 = app.mount( app2 selector );
Pretty simple you'd think given the popularity of both, but I am encountering a few hurdles.
I am using scaphold.io to be able to quickly show off a working UI. That is, if Vue can interact with Scaphold.
I have investigated two resources:
https://github.com/kristianmandrup/vue2-apollo-scaphold
Which seems to be a Scaphold production. Tried it. Many, many vague bugs.
Then there is also:
https://github.com/Akryum/vue-apollo
But this is too much. I don't need a server, the server is on Scaphold.
I also tried building the whole thing up by using the tutorial on howtographql, but this one is also outdated.
Ideally I want to instantiate an as up to date Vue 2 app using (I guess) the npm vue-cli, then install only the required apollo (or whatever, but I guess apollo) add-ons that I need. The minimum.
Shouldn't be too hard, I'll figure it out eventually, but some help is more than welcome.
You can consume a graphql api using your favorite regular request module (ajax, fetch, axios). Take the scalphold docs for example, but in the callback do this.vueUserData = body.data.getUser;
instead of
console.log(JSON.stringify(body, null, 2));
(edited to add one gotcha I remembered: if you encounter a problem where the callback doesn't know that this is supposed to be the component, you can do var self = this before the request function, then reference self.vueUserData instead.)
Does anybody know what if direct update updates everything that lives in the common directory structure. I used the same code base for multiple apps, the only change being certain settings within a js file that tells the application how to act. Is there a directory i can put that js file that would be safe from the direct update feature?
I cant seen to find any specific information on IBM's website.
I think you guys need to be careful which terms you are using in order to not confuse people who may be looking for similar help.
Environments are specific to the OS you are using. iOS, Blackberry, Android, and etc. environments.
Skins are based on the environment, and aren't generic to all platform. When you create a skin you must choose which environment you are running in.
So to correct some, direct updates will update all skin resources in targeted environments.
For example: You have an app with Android and iOS versions
When you create skins, you are creating essentially a responsive type of design to your parameters. For instance, if you have a 2.3 vs 4.2 Android OS, you can set a look and feel for both. However, these utilize a single web resource base. The APK would be the same for both versions of the app (by default) and have 2 available skins. On runtime utilizing IBM Worklight's 'Runtime Skinning' (hence the name) it goes through the parameter check for the OS and loads that skins overriding web code.
You could technically override all of the web code to be completely different for both skins, but that would be bulky and inefficient.
When you direct update you are updating all the resources of that particular environment (to include both skins), not the common folder/environment.
So an updated Android (both skins) would have updated web resources (if you deployed the android wlapp) and an iOS version would stay the same.
If you look at the Android project after build (native -> assets -> www -> default or skin) you can find the shared web resources generated by the common environment. However that is only put there every time you do a new build.
In the picture, I have an older version of the Android built for both skins on the left. On the right is a preview of the newer common resources after deploying only the common.wlapp. So you can see that they are separate.
Sorry if it was long winded, but I thought I would be thorough.
To answer the original question, have you thought of having all the parameters of the store loaded from user input or a setup? If you are trying to connect to 3 different store, create some form for settings control that will access different back ends or specific adapters. You could also create 3 different config.js that load depending on the parameters that you set so that you set. The other option is to set different versions of your apps specific to the store.
Example. Version 1.11, 1.12,1.13 can be 3 versions of the same app for store 1, 2, & 3. They can be modified and change and have 3 sets of web resources. When you need to update, jump up to version 1.21, 1.22,1.23. It seems a bit of a work around, but it may be your best bet at getting 3 versions of the same app to fall within the single application category. (keep 3 config.js types for modifying for the 3 stores).
To the best of my knowledge Direct Update will update every web resource of the skin you're using (html, css, js). However, I'm no expert with it.
If you're supporting only Android and iOS applications and need a way to store settings I recommend JSONStore. Otherwise look into Cordova Storage, Local Storage or IndexedDB.
Using a JSONStore collection called settings will allow you to store data on disk inside the app's directory. It will persist until you call one of the removal methods like destroy or until the application is uninstalled. There are also ways of linking collections to Worklight Adapters to pull/push data from/to a server. The links below will provide further details.
the only change being certain settings within a js
Create a collection for your settings:
var options = {};
options.onSuccess = function () {
//... what to do after init finished
};
options.onFailure = function () {
//... what to do if init fails
}
var settings = WL.JSONStore.initCollection('settings',
{background: 'string', itemsPerPage: 'number'}, options);
You can add new settings after initCollection onSuccess has been called:
settings.add({background: 'red', itemsPerPage: 20}, options);
You can find settings stored after initCollection onSuccess has been called:
settings.findAll({onSuccess: function (results) {
console.log(JSON.stringify(results));
}});
You can read more about JSONStore in the Getting Started Modules. See Modules: 7.9, 7.10, 7.11, 7.12. There is further information inside the API Documentation in IBM InfoCenter. The methods described above are: initCollection, add and findAll.
Since version 5.0.3 I think, direct update will not update all the webresources, only those of the skin you are using.
say you have skin def and skin skin2
you are on def
make change to def on the server -> you will get a direct update for
def only
make change to skin2 on server-> no direct update for you.
you are on skin2:
make change to skin2 on server -> direct update for skin2 only
make change to def javascript which also resides on skin2 ( and therefor end result is def+skin2 concatination), update only skin2
make change to def,just to a picture(also checking pic extension from application-descriptor: ") -> no direct update
Thats how direct update works.
Please also share some more details about what is the problem, I see you use a js file, where do you change it? what do you mean excatly, give a better (simplified) real life example, because it is unclear what you are trying.