How to create Domain on Jasper via PHP Client - php

My problem is:
i've got the PHP Client http://community.jaspersoft.com/wiki/php-client-sample-code#About_the_Class from the Jasper Community.
I want to add a Domain with PHP to the Jasper Repository and i've got the needed data in an .xml, like label etc.
In this PHP Client i have to use the class SemanticLayerDataSource to create a domain.
This class got a public variable schema.
But i can't find what this schema needs to work and add an correct domain to repository. There is not info neither on the webside nor in the class.
$semLayer = new SemanticLayerDataSource();
$semLayer->schema = ?????
$semLayer->label = (string)$xml->label; //SimpleXml
.
.
.
Which Data needs schema? An array, a resource or something else? Thank you.
Also a code sample with PHP Client would be really good, cause the documentation is not that good in this point.
Edit: I tried to create a xml as a local file a set for schema the uri of this xml. To create the xml i used this: http://community.jaspersoft.com/wiki/php-client-sample-code#Creating_Binary_Resources
I am able to create a domain, but AdHoc views on this domain doesn't work. I get a null exception from jasper.

According to the REST API docs you need to provide a schema ressource:
<schemaFileReference>
<uri>{schemaFileResourceUri}</uri>
</schemaFileReference>
This ressource represents the whole structure, as written in the domain metadata service description (under the paragraph Working with Domain Schemas):
The v2/domains/metadata service returns only the display information about a Domain, not its internal definition. The fields, joins, filters, and calculated fields that define the internal structure of a Domain make up the Domain design. The XML representation of a Domain design is called the Domain schema.
Currently, there is no REST service to interact with Domain schemas, but you can use the v2/resources service to retrieve the raw schema. First, retrieve the resource descriptor for the Domain. For example, to view the descriptor for the Supermart Domain, use the following request (when logged in as jasperadmin):
GET http://<host>:<port>/jasperserver-pro/rest_v2/resources/Domains/supermartDomain
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<semanticLayerDataSource>
<creationDate>2013-10-10 15:30:31</creationDate>
<description>Comprehensive example of Domain (pre-joined table sets for complex reporting, custom query based dataset, column and row security, I18n bundles)</description>
<label>Supermart Domain</label>
<permissionMask>1</permissionMask>
<updateDate>2013-10-10 15:30:31</updateDate>
<uri>/organizations/organization_1/Domains/supermartDomain</uri>
<version>1</version>
<dataSourceReference>
<uri>/organizations/organization_1/analysis/datasources/FoodmartDataSourceJNDI</uri>
</dataSourceReference>
<bundles>
<bundle>
<fileReference><uri>/organizations/organization_1/Domains/supermartDomain_files/supermart_domain.properties</uri></fileReference>
<locale></locale>
</bundle>
(snip) [...]
The Domain schema is an XML file with a structure explained in the JasperReports Server User Guide. If you wish to modify the schema programmatically, you must write your own parser to access its fields and definitions. You can then replace the schema file in the Domain with one of the file updating methods described in .

Well, i found the solution.
If you want to create a schema per php client, create a new file object.
$file = new \Jaspersoft\Dto\Resource\File();
$file->type = "xml";
$file->label = "MyDomain_schema";
$file->content = base64_encode((string)$schemaXML);
The file content is the base64 encoded (valid) domain schema.
Now set $semLayer->schema = $file. This way works rather good.
Also, there is a way to create the domain via multipart request, but this way is rather complicated with php client. There is a function multipartrequest in the PHP Client, but it seems that this function consists of legacy code.

Related

get filename from google docs using laravel

My site has a feature where users can upload a link to their google docs file. What I want to do is list all the uploaded links in a place. While doing that I need to show the name of the file that is associated with the link.
I can extract the file id from the link and make sure the link is of google docs. Now I need to find a way to get the filename from that. I tried going through the google developer API for google drive, but it is for uploading/doing anything only on the authorized docs. My issue here is, my users upload the files manually to their docs which I have no control over. All I get is a sharable link and somehow get the name out of it. In addition, a thumbnail will also help.
I have tried doing this, but it throws error
$url = "https://www.googleapis.com/drive/v3/files/1G6N6FyXzg7plgEtJn-Cawo5gbghrS8z9_j_cvVqcEDA";
// and
$url = "https://docs.google.com/document/d/1G6N6FyXzg7plgEtJn-Cawo5gbghrS8z9_j_cvVqcEDA/edit?usp=sharing"
$html= file_get_contents($url);
print_r($html);
A dummy link for anyone willing to help: https://docs.google.com/document/d/1G6N6FyXzg7plgEtJn-Cawo5gbghrS8z9_j_cvVqcEDA/edit?usp=sharing
Since we are getting the URL to the file, we can do a couple of things -
get the id to the file
get what type of file is that
Before I explain how to do that, it is better to know that there can be 2 possible situations. One the file is a google docs file, the other google drive file. Those both start with different URLs.
$url = explode('/', Str::after(
Str::after($request->url, 'https://docs.google.com/'), 'https://drive.google.com/'
));
I am using 2 Str::after() to remove the unnecessary part from the URL. Then I am using explode to convert the URL into an array.
Since we have excluded the useless part from the URL, we are left with document/d/1G6N6FyXzg7plgEtJn-Cawo5gbghrS8z9_j_cvVqcEDA/edit?usp=sharing in an array form.
So, if we try to do $url[2], we get the id of the file. Also, "document" is also a good thing to note about. I use those to show proper images. There can be 5 different types of them (4 for google docs and 1 for google drive). Those are - document, spreadsheets, forms, presentation for google docs, and file for google drive. I would recommend everyone store these in the database so that extra calculations are not necessary while displaying it.
Now, to answer the actual part of the question. How to get the name. I have created a new model method to handle that.
public function name()
{
$key = config('app.google_api_key');
$url = "https://www.googleapis.com/drive/v3/files/{$this->file_id}?key={$key}";
$response = Http::get($url)->json();
return $response['name'] ?? 'Private File';
}
Don't forget to add your Google API key in the config file app.php (You need to create one). You can get your API key from Google Developer Console and create a project-specific key. Just to note that this key need not be belonging to the user of the URL.
Also, a thing to note here is that $response returns error code if the file is not set to visible to the public or the file is deleted.

Azure SDK PHP SAS for container [duplicate]

I'm getting this error:
<Error>
<Code>AuthenticationFailed</Code>
<Message>
Server failed to authenticate the request. Make sure the value of Authorization header is formed correctly including the signature. RequestId:6c3fc9a8-cdf6-4874-a141-10282b709022 Time:2014-07-30T10:48:43.8634735Z
</Message>
<AuthenticationErrorDetail>
Signature did not match. String to sign used was rwl 2014-07-31T04:48:20Z /acoustie/$root 2014-02-14
</AuthenticationErrorDetail>
</Error>
I get it when I generate a sas (Shared Access Signature) then paste that sas at the end of the container uri into a browser. This is the full address with the generated sas:
https://acoustie.blob.core.windows.net/mark?sv=2014-02-14&sr=c&sig=E6w%2B3B8bAXK8Lhvvr62exec5blSxsA62aSWAg7rmX4g%3D&se=2014-07-30T13%3A30%3A14Z&sp=rwl
I have scoured SO and Google and have tried lots of combinations, as far as I can tell I'm doing everything correctly, I know I'm not, I just can't see it...really hoping someone can help :-\
To be clear, I am generating a sas on a container, not a specific blob and not on the root container. Access on the blob is defined as Public Blob. My end goal is to simply allow writes to the container with the sas, while 'debugging' I have added most permissions to the SharedAccessBlobPolicy.
I have tried adding a \ at the beginning and ending of the container name. No change.
This is the code I use to generate the sas:
var blobClient = storageAccount.CreateCloudBlobClient();
//Get a reference to the blob container
var container = blobClient.GetContainerReference(containerName);
// Do not set start time so the sas becomes valid immediately.
var sasConstraints = new SharedAccessBlobPolicy
{
SharedAccessExpiryTime = DateTime.UtcNow.AddMinutes(30),
Permissions = SharedAccessBlobPermissions.Write
| SharedAccessBlobPermissions.Read
| SharedAccessBlobPermissions.List,
};
var sasContainerToken = container.GetSharedAccessSignature(sasConstraints);
//Return the URI string for the container, including the SAS token.
var sas = string.Format("{0}{1}", container.Uri.AbsoluteUri, sasContainerToken);
Logger.Debug("SAS: {0}", sas);
return sas;
It generates a signature, it just doesn't seem to be a valid signature.
I've tried different containers, changing the Access policy, with and without start times, extending the expiry to > 12 hours from now (I'm in a UTC+10 timezone), it doesn't seem to matter what I change it results in the same "signature did not match" error.
I have even tried using an older version of 'WindowsAzure.Storage', so I have now tried 4.2 and 4.1. Even tried the uri in a different browser, really shouldn't make a difference but hey...
Any suggestions are greatly appreciated :-)
Short Answer:
Add comp=list&restype=container to your SAS URL and you should not get this error.
Long Answer:
Essentially from your SAS URL, Azure Storage Service is not able to identify if the resource you're trying to access is a blob or a container and assumes it's a blob. Since it assumes the resource type is blob, it makes use of $root blob container for SAS calculation (which you can see from your error message). Since SAS was calculated for mark blob container, you get this Signature Does Not Match error. By specifying restype=container you're telling storage service to treat the resource as container. comp=list is required as per REST API specification.
Adding to #Gaurav Mantri Answer, in order to double check the permissions, you can also create your OWN SAS token in Azure Portal
From this you can relate this comp=list&restype=container
Resource types you can provide as :
Container
Object
Service
Hope this helps to some one..
After spending lot of time on this the actual error is different then exception raised by .net compiler. if you're using meta data fields while uploading blob file into storage then check metadata character's. For example I am adding metadata fields like description, filename and etc.... In description field I have some junk characters and which i found at the run time string text viewer.
my description originally > test� file description , after changing the description "test file description" . It is working fine.
metadata values i have extracted from different sources tats why it got that junk characters . Please remove/amend values of metadata then it will work well.

PHP: How to do I post xml arguments to api?

I have to post to url : https://rightsignature.com/api/templates.xml
One of the arguments is merge_fields and the description is:
Specify the name and email of the roles returned from the prepackageTemplate call. Roles can be references by or by in the form of XML node attributes 'merge_field_name' or 'merge_field_id'. If specified by name (the easiest method), all merge fields with the name specified will take on the value specified. Optional node specifying whether to "lock" the value from the sender is availbed via .
This is what the post xml should look look like:
<merge_fields>
<merge_field merge_field_id="a_233_f309f82jklnm_232">
<value>$100 per hour</value>
<locked>true</locked>
</merge_field>
<merge_field merge_field_name="Employee Name">
<value>J. Employee</value>
</merge_field>
</merge_fields>
This is what xml response looks like:
<merge-fields>
<merge-field>
<page>1</page>
<name>Company Name</name>
<id>a_966_8bffa095998e41ecbdfb624b2fd_5671</id>
</merge-field>
</merge-fields>
Am I suppose to set it to an array like this? :
$arr= array('merge_fields'=>
array('merge_field_email'=>xxx#mail.com),
"another_field"=>"another_value")
)
https://rightsignature.com/api/templates.xml? . $arr
"Well, basically 'it's still AJAX,'" with the encoding being XML not JSON.
You would simply use appropriate XML-manipulation primitives to build and un-build your messages, as discussed here: http://php.net/manual/en/book.xml.php.
It is also possible that the API is what's called SOAP. as discussed here: http://php.net/manual/en/book.soap.php. Or, it might be XML-RPC ("XML remote procedure calls"), as discussed here: http://php.net/manual/en/book.xmlrpc.php.
All three of these pages refer to many other pages with related topics that will be highly-relevant to what you are now trying to do.
It's important that you carefully identify the exact "flavor" of API that you are dealing with, so as to use the most-powerful available libraries of existing code to deal with it at the highest possible level of abstraction. Also, do on-line research (e.g. at GitHub) to see if you can find any existing source-code that already references this API or something very-similar to it. ("Do not do a thing already done.")
The good news is, you know that you're embarking upon "a very, very familiar task" that is well-supported in PHP. And so, to borrow a Perl by-line: "there's more than one way to do it." Search for the most efficient way.

BIRT 4.5 - Disable saving connectstring inside report.rptdesign, PHP to assign connectstring

I am using Birt 4.5 and PHP/MYSQL.
I am able to run birt reports with php. I have enabled tomcat and copied 'birt-runtime-4_5_0/WebViewerExample' to tomcat/webapps and renamed it to birt.
So I can run birt viewer with php;
<?php
$fname = "report/test.rptdesign&__showtitle=false";
$dest = "http://localhost:8081/birt/frameset?__report=";
$dest .= $fname;
header("Location: $dest" );
?>
Above code is working fine. But report connectstring already saved in test.rptdesign file.
I want to remove DB login credentials from test.rptdesign file and assign it while report open with PHP.
I have tried with report parameters. But all the parameters will display on browser address-bar.
Is there any secure way to do this? This is very important when we need to change the database location. It is very hard to change the data source of each and every .rptdesign file.
Thank You,
Supun
I don't believe using report parameters to handle a database connection is the right way. In addition to the address-bar problem you mentionned, it will cause unexpected issues: for example you won't be able to use this database to feed the dataset of another report parameter.
With Tomcat the best approach is to externalize the database connection in a connection pool: easy, robust, and reports might run significantly faster.
Alternatively the datasource can be externalized in a BIRT library (.rptlibrary) and shared across all report-designs: thus only the library needs to be updated when the database location is changing.
I agree with Dominique that sending the database parameters via the query is most likely an inappropriate solution - and you've not given any explanation of whether this is a requirement of the system.
But it is quite trivial to proxy the request via PHP and decorate the URL with the required parameters, something like...
<?php
$_GET['__showtitle']=$_GET['__showtitle'] ? $_GET['__showtitle'] : 'false';
$_GET['__report']=$fname; // NB this should be NULL in your code!
$_GET['dbuser']='a_db_user';
$_GET['passwd']='s3cr3t';
$qry=http_build_query($_GET);
$url="http://localhost:8081/birt/frameset?" . $qry;
// if its simply returning HTML, then just....
$fin=fopen($url, 'r');
while ($l=fgets($fin)) {
print $l;
}
exit;
If the returned content contains relative links the you'll need to rewrite the output stream. If the content type is unusual or you want to project other headers (e.g. for caching) to the browser, then you'll need to use Curl, capture the headers and relay them.

where to put static wsdl file instead of dynamically generating the wsdl file on each request in php

Am using NuSoap Webservice. My webservice endpointType is wsdl. The problem is am not able to connect and update the status.
This is my URL
http://abc.testsite.com/LMSCallbackService/LMSExternalOrientationService.svc
Dynamically generated WSDL file Soap address location should be
http://abc.testsite.com/LMSCallbackService/LMSExternalOrientationService.svc?wsdl
But the current Soap address location is like
http://clwebwtrv4.colo.testsite.com/LMSCallBackService/LMSExternalOrientationService.svc?wsdl [the link is wrong.]
How could I remove the bold items?
I searched the stuff in net, came up with the following solutions
Use static wsdl file, instead of dynamic generation of wsdl file.
Note: don't know how to stop dynamic generation of wsdl file, also where to put the static wsdl file.
Questions:
- where to put static wsdl file?
- how to stop dynamic generation of wsdl file?
Any help?
Way to use static WSDL:
Save the wsdl file to some location, use the physical path while calling.
$url = 'http://www.testsite.com/abc/preprod_sunflower.wsdl'
Ex: $client = new nusoap_client($url,true);
Note: in that WSDL file don't fotget to provide your proper 'Soap Address Location'.
Thats it. Hope its use full.
Disadvantage:
While updating the NuSoap, its creates some problem. So we need to update our WSDL file.

Categories