Rest Services In MDriven
No edit summary
(Adding page to Category:TOC because it contains a TOC.)
 
(57 intermediate revisions by 8 users not shown)
Line 1: Line 1:
'''REST services''' are services that are executed by connecting to an URL that defines operation and parameters then it returns an answer – not seldom as JSon objects.
'''REST Services''' are services executed by connecting to a URL that defines operation and parameters and returns an answer – not seldom as JSON objects.


'''Calling existing REST services'''  
You must set the tagged value '''RestAllowed''' on the ViewModels you want to allow Rest access to.
MDriven supports a couple of EAL operators to manage REST services. All operators reside on the selfVM variable available only in the ViewModel context.
 
=== '''Calling Existing REST Services''' ===
MDriven supports a couple of EAL operators to manage REST services. All operators reside on the [[selfVM]] variable which is available only in the ViewModel context.
  ''selfVM.RestGet(targeturl,user,pwd,optionalnestingwithheaders)''
  ''selfVM.RestGet(targeturl,user,pwd,optionalnestingwithheaders)''
 
Read: [[OCLOperators RestGet]]
  ''selfVM.RestPost(targeturl,user,pwd,optionalnestingwithheadersAndUploadValues)''
  ''selfVM.RestPost(targeturl,user,pwd,optionalnestingwithheadersAndUploadValues)''
 
Read: [[OCLOperators RestPost]]
  ''selfVM.RestDownload(targeturl,user,pwd,optionalnestingwithheaders)''
  ''selfVM.RestDownload(targeturl,user,pwd,optionalnestingwithheaders)''
There is a also a new helper operator on selfVM:
Read: [[OCLOperators RestDownload]]
selfVM.JSonToObjects( «<Type>» ,  JSonDataInStringFormat)
The selfVM.JSonToObjects creates objects of class Type and matches attributes and association from the json data – and it can create object trees (unclosed graphs) by following names on associations. These few additions enables us to consume Rest services that others expose.


And when it comes to '''exposing ourselves to others''' – Turnkey has two new MVC verbs:
'''Note!''' ''optionalnestingwithheaders'' is the '''name''' of the blue ViewModel class in the example below (as an OCL String).
MDrivenRest/Get?command=vmname&id=rootobjref


MDrivenRest/Post?command=vmname&id=rootobjref
==== Example ====
What they do is that they look for ViewModel named as the command-parameter, if one is found the [http://wiki.mdriven.net/index.php/Part_9_MDriven_Turnkey,_cloud_tools_and_access_groups accessgroups] are checked to see if access is allowed. If it is, additional parameters sent in the url are matched against ViewModel variables – and given corresponding values. Then any actions present in the root level of the ViewModel are executed. And then the Get verb packs the viewmodel content as json in the response.
[[File:2018-05-29 10h31 45.png|none|thumb|689x689px]]
The action '''GetExporttest''' retrieves data by converting another ViewModel to XML - it stores it in the variable <code>vText</code>.


The Post verb looks in the request values after names that match the ViewModel root – if match is found the corresponding value is applied. Then changes – if any – are committed to db. The last thing for post is that it packs the complete ViewModel as json in the response. If there is an error – a string “error: <message>”  is returned.
The next action invokes RestPost to send that data to a URL address; it also says it should look at the nesting named 'Xml'. In this nesting, we have the STRINGCONTENT (see also [[OCLOperators RestPost]]) which gets its content from the vText variable. We also add the header Authorization with a bearer token to get access from the receiving service.


You must set RestAllowed on ViewModels you want to allow Rest access to.
=== Exposing Ourselves as a REST Service ===
When it comes to '''exposing ourselves to others''' – Turnkey has two MVC verbs, Get and Post, like this:
TurnkeyRest/Get?command=vmname&id=rootobjref
TurnkeyRest/Post?command=vmname&id=rootobjref
New(2023-04):
--- if you have a varible vRestVerb it is assigned the verb used
TurnkeyRest/Put?command=vmname&id=rootobjref
TurnkeyRest/Patch?command=vmname&id=rootobjref
TurnkeyRest/Delete?command=vmname&id=rootobjref
use Disable/ReadOnly expression on actions to decide what to run: vRestVerb<>'Put' -- readonly for all but Put


<html>
See [[Improved routes]] for other URLs.  
<p1>
<em>To make your experience more comfortable, we set the main tags mentioned in the video to the right bar menu of this mini player. Choose the interesting subtitle on the list and immediately get to the exact theme timeplace in the video. Now you can pick any topic to be instructed without watching the whole video.</em>
<style type="text/css">
p1 {
opacity: 0.7;
text-align: justify;
width: 90%
}
</style>
</p1>
<style>
#video12 {
  position: relative;
  height: 500px;
  width:560px;
  padding-bottom: 10px;
}
#video12 iframe {
  position: absolute;
  min-height: auto;
  min-width: auto;
}
#video12 div {
  position: absolute;
  top: 0;
  left:760px;
  width: 260px;
  height: 100%;
  padding-left: 10px;
  overflow-y: auto;
}
span {
    font-size: 18;
    display:block;
  padding: 2px 10px 2px 10px;
    padding-bottom: 0.5;
    padding-top: 0.5;
  opacity: 0.7;
}
span:hover {
  color: #0000FF;
  cursor: pointer;
}
span:focus {
  color: blue;
</style>


</br>
The ViewModel name is supplied as the '''command''' parameter.
<div id="video12">
<iframe width="740" height="500" src="https://www.youtube.com/embed/MKlQD8F1mz8?rel=0&autoplay=0" frameborder="0" allowfullscreen></iframe>
  <div>
    <span data-video="MKlQD8F1mz8" data-start="5" tabindex="0"> What is REST? </span>
    <span data-video="MKlQD8F1mz8" data-start="77" tabindex="0"> How does it work with MDriven turnkey? </span>
    <ul>
    <span data-video="MKlQD8F1mz8" data-start="120" tabindex="0"> calling an existing REST service </span>
    <span data-video="MKlQD8F1mz8" data-start="186" tabindex="0"> exposing ourself as REST service </span>
    <ul>
    <span data-video="MKlQD8F1mz8" data-start="239" tabindex="0"> MDriven turnkey app slot </span>
    <span data-video="MKlQD8F1mz8" data-start="328" tabindex="0"> how to expose information as the Rest service? </span>
    <span data-video="MKlQD8F1mz8" data-start="445" tabindex="0"> MDriven Rest/get strategy </span>
    </ul>
    <span data-video="MKlQD8F1mz8" data-start="568" tabindex="0"> how to consume data? </span>
    <ul>
        <span data-video="MKlQD8F1mz8" data-start="675" tabindex="0"> selfvm </span>
        <span data-video="MKlQD8F1mz8" data-start="711" tabindex="0"> Rest/Get operator </span>
        <span data-video="MKlQD8F1mz8" data-start="920" tabindex="0"> hard-coded objects </span>
    </ul>
    <span data-video="MKlQD8F1mz8" data-start="1331" tabindex="0"> Json to objects operator </span>
    <span data-video="MKlQD8F1mz8" data-start="1779" tabindex="0"> update data with allow post </span>
    <ul>
    <span data-video="MKlQD8F1mz8" data-start="1893" tabindex="0"> RestPost operator as a post command </span>
    <span data-video="MKlQD8F1mz8" data-start="2485" tabindex="0"> operation execution</span>
    <span data-video="MKlQD8F1mz8" data-start="2553" tabindex="0"> vSomeParam adding new parameters </span>
    </ul>
   


The '''id''' parameter is an object reference in one of several available formats. Read more [[The ExternalId explained|here]] about how to create these.


'''Caution''': Always send a complete ID, i.e. a guid or '''xx|yyyy'''. Using a shortcut without a class identifier can cause problems.


</div>
Note that the variables set in your ViewModel have to be of the '''String''' type.
</div>


<script>
===== The Commands Do This: =====
var IMG = document.querySelectorAll('#video12 span'),
We check that the tagged value '''RestAllowed''' has been set on the ViewModel, then look up the root object.  
    IFRAME = document.querySelector('#video12 iframe');
for (var i = 0; i < IMG.length; i++) {
  IMG[i].onclick = function() {
    IFRAME.src = 'http://www.youtube.com/embed/' + this.dataset.video + '?rel=0&autoplay=1';
    if(this.dataset.end) IFRAME.src = IFRAME.src.replace(/([\s\S]*)/g, '$1&end=' + this.dataset.end);
    if(this.dataset.start) IFRAME.src = IFRAME.src.replace(/([\s\S]*)/g, '$1&start=' + this.dataset.start);
    this.style.backgroundColor='rgba(0,0,0,.2)';
  }
}
</script>
</html>


'''Raw subtitles text'''
When the ViewModel and its root have been found, we check the [http://wiki.mdriven.net/index.php/Part_9_MDriven_Turnkey,_cloud_tools_and_access_groups accessgroups] to see if access is allowed.


Rest services and MDriven turnkey, so Rest
Then additional parameters are set (these can be either URL Encoded or multi-part form-encoded. [https://developer.mozilla.org/en-US/docs/Web/HTTP/Methods/POST See HTTP POST] for details).
* For Get, the parameter names are looked up against ViewModel variables, and variable values are set.
* For Post, the parameter names are looked up against ViewModel variables, '''and''' '''attributes''' and values are set.
Then any actions present at the root level of the ViewModel are executed - ''in the order presented in the ViewModel'' from top to bottom.
* For Get, use the actions to look up additional information.
* For Post, the actions are usually used to process sent JSON data into objects (see below)
Post saves any changed values to the database.


is a very powerful simple way to access
Both Get and Post return the ViewModel content as JSON in the HTTP response. To override this, use one of these strategies:
# Add a string attribute named exactly RawJSon on the root - if found, this is returned instead of the complete VM as JSON. 
#  Add a vReturnMessage:String variable as described further down this page
If there is an error, a string “error: <message>”  is returned.


web services on the web and retrieving
If you need to receive Post data unknown at design time, please read: [[Receive post data not known at design time]].


information from really anyone
You may [[Use c-sharp code to post to TurnkeyRest|use C# code to post to TurnkeyRest]].


so there's a growing catalog of available
===== Processing JSON into Objects =====
If you want to send data as JSON in a POST, you need to apply the JSON string to your system's modeled objects.


web services, that deliver rest type
Use [[Tajson]] or the simpler JsonToObjects. Read more here on XML or JSON support: [[Import xml and JSon with MDriven]]


messages just to name a few and you
The selfVM.JSonToObjects creates objects with the root of a class and matches attributes and associations from the JSON data – it can create object trees (unclosed graphs) by following names on associations.
selfVM.JSonToObjects( «<Type>» ,  JSonDataInStringFormat)
You can use an existing JSON as a template to create a model section you can import into - see: [[Using JSON or XML as class template|Using JSON or XML as a class template.]]


could get the things from Spotify to get
=== Video ===


artists or seek their catalog with
<html>
<p class="warn">
  <em>To make your experience smooth, we set the main tags mentioned in the video to the right bar menu of this mini-player. Choose an interesting subtitle on the list and immediately get to the exact theme navigation item place in the video. Now you can pick any topic to be instructed on without watching the whole video.</em>
</p>
<br>
<div class="video">
  <div class="video__wrapper">
    <iframe src="https://www.youtube.com/embed/rv31ziYXWME?rel=0&autoplay=0" frameborder="0" allowfullscreen></iframe>
  </div>
  <div class="video__navigation">
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="10" tabindex="0"> What is REST? </span>
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="82" tabindex="0"> How does it work with MDriven Turnkey? </span>
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="125" tabindex="0"> Calling an existing REST service </span>
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="191" tabindex="0"> Exposing ourselves as REST service </span>


resting interfaces you could call on
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="244" tabindex="0"> MDriven Turnkey app slot </span>
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="333" tabindex="0"> How to expose information as the Rest service? </span>
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="450" tabindex="0"> MDriven Rest/Get strategy </span>


services to upload the word documents to
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="573" tabindex="0"> How to consume data? </span>


get the PDF in return, you could up
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="680" tabindex="0"> selfvm </span>
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="716" tabindex="0"> Rest/Get operator </span>
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="925" tabindex="0"> Hard-coded objects </span>


request the email sent in your name etc
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="1336" tabindex="0"> Json to objects operator </span>
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="1784" tabindex="0"> Update data with allow post </span>


so it's a very powerful way to get
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="1898" tabindex="0"> RestPost operator as a post command </span>
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="2490" tabindex="0"> Operation execution</span>
    <span class="navigation-item" data-video="rv31ziYXWME" data-start="2558" tabindex="0"> vSomeParam adding new parameters </span>


both information and functionality


from other providers, so how does it
  </div>
</div>


work with MDriven turnkey, well there
</html>
 
actually two kinds of needs one kind
 
is calling existing rest services and
 
the other one is to expose our self as
 
rest services, so we're going to look at
 
both today and there's a new article out
 
rest services and  MDriven turnkey
 
so calling an existing rest service
 
there are new ocl operators on the selfVM class
 
so you can call a target URL
 
and get data back and you can post to
 
target URL or you can download and this
 
is the case when you have requested
 
something bigger like a file being
 
produced for you or something
 
there's also a method to convert JSon
 
that you have in a string
 
to objects in your model
 
so that it will be easier to work on, with the data and with the tools
 
you know from MDriven designer and the
 
second thing that we're going to talk
 
about is exposing our selves as rest services
 
and this is actually a functionality of MDriven turnkey
 
so there's an MDrivenRest/get that
 
takes a command which actually is
 
ViewModel name and the root object and there is
 
an MDriven post and we're going to see
 
how these two simple mvc verbs will
 
actually solve, I believe,
 
all problems for us, so let's dive into
 
some example, I have this model from before
 
it resides in my MDriven turnkey 006 app slot
 
and it has a few things like show
 
all cars and once on a car you could
 
click it and view edit one car and then it has the override and I
 
don't want this in this case I'm gonna
 
remove that, I'm going to go off screen
 
so I'm back and this is the default view
 
that was rendered for us
 
given the view model that
 
looked like this, right, so what we can do now
 
is to try an access this information
 
try to expose this same information as the rest service
 
in order to do that, we need to select
 
the head of the view model and set this new property
 
this is initially false, but if we want a
 
view to act as a data source available
 
from a Rest request, we need to set Rest
 
allowed to true like that and once we have done that I'm also
 
gonna add and remove this action just
 
not to confuse we're going to come back to this later
 
so you're setting a comment on this one
 
and it should do judt something to be okay
 
we're gonna leave it like that and so
 
can we turn this information as rest
 
well now we have said it allow, said that
 
it was allow Rest, so we're going to
 
upload that, so that our turnkey site
 
works on this view model and check status
 
and we're done to get this, we could
 
simply try an access our site with the
 
new strategy that was said here MDrivenRest/get
 
like this, like so, but we want to have this view model and this
 
root object,so let's paste in the view
 
model name and the root object reference
 
that shouldn't be there, like this
 
executing that returns our data as a Rest
 
document, so let's check this out
 
registration number F F X Y if I were to
 
change it here to my new car is FPT128
 
that's really cool, because that's
 
almost as ftp and 128 is really
 
important number to me because it's well
 
binary and so I'm quite happy with my
 
registration number on your card that's
 
that's finally one I can remember and
 
save that and as I have saved that and
 
hit this one again, I can see that it updates
 
ok so this is one way to expose ourselves as a rest service
 
let's try and consume ourselves that
 
sounds weird, but what I mean is that we
 
could add a viewmodel, well if I'm not
 
locked by the model dialogue, let's add a
 
new view model and let's call this
 
consume our self, weird and going to root that in car and say that
 
let's add a class action for show
 
meaning that whenever we see a car there
 
should be an action that could take us
 
here, having done that I should see
 
that there is a class action car
 
view consume self and if I would wanted to fix
 
up that action I could do that here
 
calling it something else but
 
this is fine so what I want to do here
 
is I can add the registration number
 
just to see that, we have it and
 
then I could add a column prepared for action which really is
 
generic column with this one checked and
 
try and get by rest, so that's an action
 
that we're gonna call to try and consume
 
to get this information, so basically we
 
would want to do this in here
 
and selfvm is the one that has the new
 
rest operators, rest get and I'm not
 
been a little fast, because rest get
 
If I point at this I see the tooltip stating that
 
the first argument is the target URL
 
then it's a user and the password and
 
then it's the name of a nesting so for
 
now I'm just going to use the target URL
 
as the first param I'm going to leave the
 
other ones blank, so paste in that blank
 
blank the password and the nesting blank
 
and I didn't chose it correctly, so rest get, ok, so but that yes return
 
something that we need to store it somewhere
 
let's add a veriable to do this
 
viewmodel just to show on the root
 
I'm gonna do add variable which means
 
that again one new hear, can call it
 
that it's a string in here I can assign
 
the return value to this like this
 
then I could add a generic column with
 
the expression of the value of the new
 
variable, so we don't get confused going
 
to make this a little bigger like this, so what I want to do is to
 
push this button and I want to get this
 
information in this variable, can I do that
 
well, I'm uploading the model
 
check status and then I close it
 
and then I head back here and no
 
that's not the place, here and I refresh
 
this one, so we got a new action
 
view consume ourselves, right, sounds weird but
 
let's do it, I'm going to press ctrl to
 
get a new tab, fault I did test that again
 
press ctrl ok there's something wrong
 
with my language settings of the
 
control keys and targeted, so this is
 
the registration number and trying
 
get Rest and I get the same information right but as you note
 
this was like hard-coded to one specific card
 
the root ID which would mean that
 
doesn't really matter, what car I took
 
in here, if I took this one 12345 and
 
consume I would still get the ftp car
 
because that was hard-coded in here
 
so instead of doing this I would like to
 
just add the self, as I'm rooted,
 
the views was rooted in a car
 
externalid like that,  in that way
 
it would be new data for each,
 
for the rooted object, let's try that out
 
upload and refreshing it
 
okay, it wasn't done, refreshing it again, it was done
 
try and get by rest and now we see that
 
it is updated, now let's see what happens
 
if I change this, seven,and what should
 
happen when I try and get by rest well let's see what happens
 
it returns the same thing
 
why because I haven't saved yet so this
 
is running in its own and this is a new
 
query against the database and the data
 
that's actually in the database not the
 
data that this session is changing, so if
 
I save this and then press this one I
 
get the "seven" right nothing strange about that
 
and just important to know that the
 
rest operations running their own space
 
ok just to ensure that we could call anyone
 
let's do, let's copy this one and put it
 
below and call it get stuff from spotify by
 
I was on the spotify developer page
 
finding out how to formulate a query and I have it here
 
so and it says query - Metallica and
 
type- artist so that would assign it
 
to the new variable as well that would
 
be fine just testing, uploading and
 
refreshing get stuff from Spotify that
 
we get a bunch of data from from there
 
if we would want to do more advanced
 
stuff with this like here we let's see
 
what is the data want to copy that copy
 
and I'm gonna bring it up in the most
 
versatile tool yet ever invented, the notepad
 
yeah, whatever artists' it says it has a
 
link with artists that goes to here
 
no here is this one
 
well it might not be the most brilliant tool
 
this not bad anyhow, but what I want
 
to do is to be able to read some of the
 
things here like, I want to convert it to
 
objects and these are properties of
 
the artists object, so and how would I go about that
 
well I could use the new operator self
 
selfVM was calling something with
 
Json to objects and it takes a
 
type and a string with Json, the type is
 
actually what kind of root object it
 
should create from the Json and let's see
 
and let's just say that we don't have
 
that yet, but we have this one it's the
 
vNew variable, but we need to have
 
somewhere where to store the date
 
that we get, let's add a new diagram or
 
rather just do it here and a class data
 
from spotify and class artist
 
that has the relation called artist
 
why, because that what it was
 
called in the data, so like that and we
 
want to get this attribute maybe that we
 
need to match it with an attribute here
 
and items we might not care about
 
let's see how does this data
 
it has a name, so going to add that as well,
 
so this is the objector we could create and then
 
it will follow the data and create these as
 
well that's the general ID idea like that data from spotify
 
take the values from there and just to
 
see turn into object call this one
 
and how can we verify that it works
 
add the nesting this one going
 
to be our test all instances right and
 
it's gonna be hooked up to it this one
 
call this one artist and the type will
 
be artist as well and we grab the
 
properties that we have in it href and the name
 
let's see how this will work out for us
 
again upload check that we're done
 
now it's great that the table for the artist
 
and things like that, so no need to call
 
the DBA today, we can manage ourselves
 
opening up this one consume
 
ourelves and get stuff from Spotify and
 
turn into objects and it found and href
 
but it couldn't match to query metallic
 
offset let's do the same question hereitems, images
 
these are only images , so it's all the way down here maybe, no
 
that's another one, okay I'm gonna figure this out I'm going off screen
 
ok now I think I got it, it's the items
 
property that holds all the results so
 
for this to work we would need to
 
actually introduce something in between
 
here called the result set and there is
 
the one that holds to our tests and
 
then there would be an association here
 
called items, this is how this data
 
looks, so upload that instead
 
good thing I didn't involve the DBA
 
because he would rip my head off because
 
I haven't checked thoroughly enough
 
before asking him to do work for me
 
so cancel and refresh this one, get stuff
 
from Spotify turn into objects
 
metallica, metalica with Ozzy Osborne,
 
Lou Reed right so I could choose to save
 
this and then I would have those objects
 
and that would be some kind of reference
 
data for my system to work with or
 
consider to make this class transient
 
and ask for it every time
 
still you can do anything you need with
 
this strongly typed information once you
 
have the reference it from from the Json
 
right that was then turn into objects
 
Json turning to objects operator,Json to
 
objects and is there anything left to
 
show you, yes you will want to allow post
 
to your own data, so what if we try and
 
get by Rest and we want to post back a
 
new registration number or other
 
just want to post back a new
 
registration to update supervine
 
let's add a veriable to have hold the new
 
registration number, vNewRegNum  okay
 
and let's add a cgeneric column that has
 
that expression and let's not call it
 
exact the same thing as the other one
 
because that's not allowed and put it
 
put it here and put it below and I'm
 
gonna make it smaller and below, like that
 
yep that's fine, that's fine
 
so I have a new registration number, now
 
I actually want to post that back to my
 
rest post, I want to send back to
 
myself, so we need an action for that
 
it sort of looks like this one,
 
UpdateRegNumViaRestPost ok going to change this one
 
to rest post, bring up that view editor
 
with some expression just to check
 
how does it selfVM.RestPost it has
 
four parameters all strings, target URL
 
user password and name of nesting ok
 
what it says after in the end is
 
adds data in nesting and it also says that
 
file name underscore something
 
with upload that something column with
 
filename from filename underscore something,  so that's
 
advanced we will leave that for later
 
but what it says that it needs a
 
nesting to hold the data that we
 
gonna post up, so assume that we call
 
that nesting data to post
 
published and we send that in and then
 
we add other nesting and we say it's data to post
 
and it's of type
 
well it don't care really because we're
 
going to add the variable at the generic
 
column and in this column
 
we're gonna use variable vNewRegNum
 
like that and now it's important
 
that what we're going to post up we're
 
going to post it to this view model called edit one car
 
ok, so that's add it one car, but what
 
what does it expect, well edit
 
on car has these properties, this is what
 
what will be exposed as the rest
 
what we can set by rest registration
 
number it's called right, so we head back
 
to the consume and we call this one
 
registration... no I was wrong, ctrl+z to call this one registration
 
so what we say here is that and grab
 
grab do rest post to ourselves, but this could
 
be anywhere, because we got the full URL
 
on the command "edit one car" with ID
 
as ourselves the rooted object
 
from this view that we are in and use
 
data to post nesting, to get data
 
so it will upload a multi-part rest
 
message with at least this column
 
registration number and set to the
 
variable that we have assigned our
 
variable and after that it will get the
 
return result and how rest post works in
 
and MDriven is that it will return the
 
complete as from get, if everything is ok
 
so that is enough to try it out
 
upload model, check status, done refresh
 
so now we have this registration number and if we will get
 
to get it we see that it's this one and
 
we set something else so now our variable has
 
the value something else and we try to
 
update the registration number by
 
calling a post request back to ourselves
 
seems like nothing happened, going off screen
 
ok I'm back and I figured the problem out
 
and actually this when I say data to
 
post it's important that its existing
 
as a name here, so it will be found so
 
self and back is associated to the data post
 
this this is small screen here
 
well, this one goes up here come back here
 
maybe we should do something like this
 
to better fit on the screen
 
that was the first error but I did another thing wrong as well in my
 
URL even if I said that it was the
 
command rest post, which will be
 
a post command on I actually had from the
 
copypaste to get verb on our server
 
our server thought, that well I'm not
 
gonna post anything because this is a get
 
so no data was actually applied, so having fix those things and
 
of course it's just common sense when
 
you post you need to go to
 
the post endpoint and when you get you do it
 
from the get endpoint and once that is done
 
and I uploaded the model with
 
those changes I get refresh the view
 
I can now enter something else on
 
the registration number and update via
 
post and this one is returned with registration numbers
 
something number something else
 
so we have shown how we can expose
 
ourselves as rest services and we have
 
also shown how we can update via rest
 
services we have shown how we can
 
consume others how we can consume the
 
JSon result from others to create the objects in our model and
 
what's left well one cool thing that we need to show
 
is the ability to actually execute
 
operations because this becomes
 
important if you want to do delete maybe
 
some kind of complex operation on
 
your data before returning, actually it's
 
quite easy and we saw it already because
 
I had it in the test sample I guess
 
on the one that we have enabled rest for
 
allow rest- edit one car we can have it
 
actions all actions available on the
 
root level will actually be executed
 
they will be executed on gets and they
 
will be executed on posts, so this is important to remember
 
we can actually do stuff here, so remember
 
if I've commented this out before you
 
comment it back again, so what it says here is that
 
registration number should equals itself
 
plus something and here it says some
 
param and this is another important
 
aspect that we can send in more
 
parameters on the command line or on the URLs
 
parameters, HTML parameters, so what is
 
this that's actually just a veriable
 
defined here with some param as string
 
and that would be nothing I guess if we
 
don't have a default value, let's set the
 
default value, something and upload model
 
and this reloads something else
 
is registration number
 
and we got this, we didn't get the default value
 
let's see if I put that wrong I
 
can't really remember with default value
 
is going, think it's going in the other one
 
uploading the model off-screen, refreshing this
 
what happened now, unbracket, check
 
status and that probably wasn't a good place to
 
have it and see if everything is work
 
you see localhost I'm in the
 
wrong place,something else
 
something else, oh and apparently I shouldn't have had
 
their asteriskes that so the value is
 
actually something else, but since the
 
action executes before it returns from
 
the get it appends this so this isn't
 
actually saved, but what if I were to do the same on the post
 
well I say that the new registration
 
number should be www and update
 
I sort of expected that to become
 
and never mind
 
so can we change this value to
 
something else by sending in something
 
else on that URL
 
yes, we can consume ourselves and we
 
have this place here and we can just
 
send in let's add some more parameters
 
and they are separated by n and we call
 
that one well now the short-term memory problem
 
appears I don't remember
 
what do we call it, on card call it
 
vSomeParam, consume, hello,
 
so I can send data and one that's actually
 
interesting, didn't update if anyone can
 
help me find that error, ok and back here
 
upload and trying it rest,now it's hello
 
because that's what we sent on that we


sent on on the command line or a day in
=== Return Status Codes and Override Returned Data ===
'''New from 2020-12-09:''' You can now override return result data and code by declaring variables in your RestAllowed ViewModel:


the URL alright so this is a short introduction
vReturnMessage:String
vReturnStatusCode:String
The vReturnMessage (reason code) must be found and will be returned as content instead of the default (to make JSON of the ViewModel). The return message will have the status code "vReturnStatusCode".


on how to work with them rest interfaces
If the vReturnStatusCode is found, it must have one of the values defined here: https://docs.microsoft.com/en-us/dotnet/api/system.net.httpstatuscode?view=net-5.0 Otherwise, 200 "Ok" is returned. We will parse the string value with this logic:
realstatuscode = (System.Net.HttpStatusCode)System.Net.HttpStatusCode.Parse(typeof(System.Net.HttpStatusCode), (string)(returnstatuscode.AsObject), true);
This means the action code can look like this:  
vReturnStatusCode:='NotFound' or vReturnStatusCode:='Created' etc


both consuming information from others
=== Read Status Code from RestPost, RestGet, etc ===
Use the vReturnStatusCode:string variable name to get Status from querying others with rest - RestPost, RestGet, etc.


and exposing information from ourselves
Use the vReturnMessage:string variable name to get the reasoncode from others with Rest.


and it's quite powerful and you can do a
=== Receive String Content ===
We assume postback data as FormFields that we match to ViewModelColumns. If someone posts string content (no form data), we now put that data in a column named "STRINGCONTENT" if found.


lot of things and it's good when
== Debugging ==
It may sometimes be time-consuming to get all the parameters correct when forming a request. A tip is to use postman-echo.com [https://postman-echo.com] to better understand what is sent.


integrating both functionality and
[[Category:Rest]]
[[Category:Advanced]]
{{Edited|July|12|2024}}


information services into your system
[[Category:TOC]]

Latest revision as of 14:13, 26 March 2024

REST Services are services executed by connecting to a URL that defines operation and parameters and returns an answer – not seldom as JSON objects.

You must set the tagged value RestAllowed on the ViewModels you want to allow Rest access to.

Calling Existing REST Services

MDriven supports a couple of EAL operators to manage REST services. All operators reside on the selfVM variable which is available only in the ViewModel context.

selfVM.RestGet(targeturl,user,pwd,optionalnestingwithheaders)

Read: OCLOperators RestGet

selfVM.RestPost(targeturl,user,pwd,optionalnestingwithheadersAndUploadValues)

Read: OCLOperators RestPost

selfVM.RestDownload(targeturl,user,pwd,optionalnestingwithheaders)

Read: OCLOperators RestDownload

Note! optionalnestingwithheaders is the name of the blue ViewModel class in the example below (as an OCL String).

Example

2018-05-29 10h31 45.png

The action GetExporttest retrieves data by converting another ViewModel to XML - it stores it in the variable vText.

The next action invokes RestPost to send that data to a URL address; it also says it should look at the nesting named 'Xml'. In this nesting, we have the STRINGCONTENT (see also OCLOperators RestPost) which gets its content from the vText variable. We also add the header Authorization with a bearer token to get access from the receiving service.

Exposing Ourselves as a REST Service

When it comes to exposing ourselves to others – Turnkey has two MVC verbs, Get and Post, like this:

TurnkeyRest/Get?command=vmname&id=rootobjref

TurnkeyRest/Post?command=vmname&id=rootobjref 

New(2023-04):
--- if you have a varible vRestVerb it is assigned the verb used 
TurnkeyRest/Put?command=vmname&id=rootobjref 
TurnkeyRest/Patch?command=vmname&id=rootobjref 
TurnkeyRest/Delete?command=vmname&id=rootobjref 

use Disable/ReadOnly expression on actions to decide what to run: vRestVerb<>'Put' -- readonly for all but Put

See Improved routes for other URLs.

The ViewModel name is supplied as the command parameter.

The id parameter is an object reference in one of several available formats. Read more here about how to create these.

Caution: Always send a complete ID, i.e. a guid or xx|yyyy. Using a shortcut without a class identifier can cause problems.

Note that the variables set in your ViewModel have to be of the String type.

The Commands Do This:

We check that the tagged value RestAllowed has been set on the ViewModel, then look up the root object.

When the ViewModel and its root have been found, we check the accessgroups to see if access is allowed.

Then additional parameters are set (these can be either URL Encoded or multi-part form-encoded. See HTTP POST for details).

  • For Get, the parameter names are looked up against ViewModel variables, and variable values are set.
  • For Post, the parameter names are looked up against ViewModel variables, and attributes and values are set.

Then any actions present at the root level of the ViewModel are executed - in the order presented in the ViewModel from top to bottom.

  • For Get, use the actions to look up additional information.
  • For Post, the actions are usually used to process sent JSON data into objects (see below)

Post saves any changed values to the database.

Both Get and Post return the ViewModel content as JSON in the HTTP response. To override this, use one of these strategies:

  1. Add a string attribute named exactly RawJSon on the root - if found, this is returned instead of the complete VM as JSON.
  2. Add a vReturnMessage:String variable as described further down this page

If there is an error, a string “error: <message>” is returned.

If you need to receive Post data unknown at design time, please read: Receive post data not known at design time.

You may use C# code to post to TurnkeyRest.

Processing JSON into Objects

If you want to send data as JSON in a POST, you need to apply the JSON string to your system's modeled objects.

Use Tajson or the simpler JsonToObjects. Read more here on XML or JSON support: Import xml and JSon with MDriven

The selfVM.JSonToObjects creates objects with the root of a class and matches attributes and associations from the JSON data – it can create object trees (unclosed graphs) by following names on associations.

selfVM.JSonToObjects( «<Type>» ,  JSonDataInStringFormat)

You can use an existing JSON as a template to create a model section you can import into - see: Using JSON or XML as a class template.

Video

To make your experience smooth, we set the main tags mentioned in the video to the right bar menu of this mini-player. Choose an interesting subtitle on the list and immediately get to the exact theme navigation item place in the video. Now you can pick any topic to be instructed on without watching the whole video.


What is REST? How does it work with MDriven Turnkey? Calling an existing REST service Exposing ourselves as REST service MDriven Turnkey app slot How to expose information as the Rest service? MDriven Rest/Get strategy How to consume data? selfvm Rest/Get operator Hard-coded objects Json to objects operator Update data with allow post RestPost operator as a post command Operation execution vSomeParam adding new parameters

Return Status Codes and Override Returned Data

New from 2020-12-09: You can now override return result data and code by declaring variables in your RestAllowed ViewModel:

vReturnMessage:String
vReturnStatusCode:String

The vReturnMessage (reason code) must be found and will be returned as content instead of the default (to make JSON of the ViewModel). The return message will have the status code "vReturnStatusCode".

If the vReturnStatusCode is found, it must have one of the values defined here: https://docs.microsoft.com/en-us/dotnet/api/system.net.httpstatuscode?view=net-5.0 Otherwise, 200 "Ok" is returned. We will parse the string value with this logic:

realstatuscode = (System.Net.HttpStatusCode)System.Net.HttpStatusCode.Parse(typeof(System.Net.HttpStatusCode), (string)(returnstatuscode.AsObject), true); 

This means the action code can look like this:  

vReturnStatusCode:='NotFound' or vReturnStatusCode:='Created' etc

Read Status Code from RestPost, RestGet, etc

Use the vReturnStatusCode:string variable name to get Status from querying others with rest - RestPost, RestGet, etc.

Use the vReturnMessage:string variable name to get the reasoncode from others with Rest.

Receive String Content

We assume postback data as FormFields that we match to ViewModelColumns. If someone posts string content (no form data), we now put that data in a column named "STRINGCONTENT" if found.

Debugging

It may sometimes be time-consuming to get all the parameters correct when forming a request. A tip is to use postman-echo.com [1] to better understand what is sent.

This page was edited 55 days ago on 03/26/2024. What links here