пятница, 1 марта 2019 г.

How to make SAP JPA Entity on SAP Enterprise portal for SQL Server Database

I need to create SAP JPA Entity for SAP Enterprise Portal for work with SQL Server:

1. I Create ejb module project (EJB) and Enterprise Project (EAR).
2. Right clikck on mouse on ejb project and select JPA Tools -> Generate Entities from Tables
3. On wizard click on Add connections.
4. Select SQL Server
5. Next click on New Driver Definition, select 2008 JDBC Driver, on tab JAR List delete default driver and add your driver for DB (For java 8 you need jdbc4 driver). Click OK.
6. Input connection properties and next
7. Next you have connected to DB, choose schema and select your table to generate entity.
8. Next generate Entity as usual. JPA need uniqe id field in table. If you created table with identity id, you can specify GenerationType.IDENTITY.
9. On SAP EP go to nwa -> Application Resources.
10. Create new Custom Data Source.

  • Driver name: SYSTEM_DRIVER
  • SQL Engine: Vendor SQL
  • Isolation Level: Default
  • Driver Class Name: com.microsoft.sqlserver.jdbc.SQLServerDriver
  • Database URL: jdbc:sqlserver://<host>:1433;databaseName=DB
  • User and pass.

11. In your EAR component specify your datasource from previous step:
<data-source-name>YOUR_DATASOURCE</data-source-name>.
12. Deploy

среда, 27 декабря 2017 г.

Stemming Apache Lucene example Russian language

Example of Stemming Apache Lucene - Russian language:


String querystr = "Проводнику большие";

Analyzer analyzer = new RussianAnalyzer(Version.LUCENE_40);

Directory index = new RAMDirectory();

IndexWriterConfig config = new IndexWriterConfig(Version.LUCENE_40, analyzer);

IndexWriter w = new IndexWriter(index, config);
addDoc(w, "Проводник большой", "193398817");
addDoc(w, "Проводнику большому", "55320055Z");
addDoc(w, "Проводные большие", "55063554A");
addDoc(w, "Большие проводники", "9900333X");
w.close();

Query q = new QueryParser(Version.LUCENE_40, "title", analyzer).parse(querystr);

int hitsPerPage = 10;
IndexReader reader = DirectoryReader.open(index);
IndexSearcher searcher = new IndexSearcher(reader);
TopScoreDocCollector collector = TopScoreDocCollector.create(hitsPerPage, true);
searcher.search(q, collector);
ScoreDoc[] hits = collector.topDocs().scoreDocs;

System.out.println("Found " + hits.length + " hits.");
for (int i = 0; i < hits.length; ++i) {
int docId = hits[i].doc;
Document d = searcher.doc(docId);
System.out.println((i + 1) + ". " + d.get("isbn") + "\t" + d.get("title"));
}

reader.close();

вторник, 12 декабря 2017 г.

How to call SAP BPM OData service api from jQuery ajax

How to call SAP BPM OData service api from jQuery ajax.

Call with "GET" method:
If you want to call BPM OData service via http "GET" method, then you just call it via jQuery $.ajax.

Call with "POST" method:
If you want to call BPM OData service via http "POST" method, then first you have to call some BPM OData service with "GET" method with http header 'x-csrf-token' with value 'Fetch' to get token. Then you have to call BPM OData service with "POST" method and you have to set 'x-csrf-token' header which you recieved in previous step.

Example:

<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>

<div class="MyTest">Hello</div>
<div class="result1">result1</div>
<div class="result2">result2</div>

<script type="text/javascript">

$.ajax({
    url: "http://<server>:<port>/bpmodata/processes.svc/ProcessCollection('<bpm process id>')?$format=json",
    headers: {     
        'x-csrf-token':'Fetch',     
    },
    method: 'GET',
    success: function(data, textStatus, request){
var myToken = request.getResponseHeader('x-csrf-token');                
        $(".result1").html(myToken);

        $.ajax({
            url: "http://<server>:<port>/bpmodata/processes.svc/Cancel?InstanceId='<bpm process id>'&$format=json",
            headers: {     
                'x-csrf-token': myToken,     
            },
            method: 'POST',
            success: function(data, textStatus, request){                
                $(".result2").html('completed');
           },
           error: function (request, textStatus, errorThrown) {
                alert('Error');
           } 
        });
     
   },
   error: function (request, textStatus, errorThrown) {
        alert('Error' + request.getResponseHeader('x-csrf-token'));
   }

 
  });

</script>

</body>
</html>

понедельник, 20 ноября 2017 г.

JDBC get Connection MySql MS SQL

public static Connection getConnection() {

  //MySql
Class.forName("com.mysql.jdbc.Driver");

  //MS SQL
Class.forName("com.microsoft.sqlserver.jdbc.SQLServerDriver");

String url = PortalHelper.getAppProperties("DATABASE_URL");
String name = "JDBC_USER_NAME";
String password = "JDBC_USER_PASSWORD";

return DriverManager.getConnection(url, name, password);
}

четверг, 25 августа 2016 г.

Make JPA Entity with @OneToMany and @ManyToOne mapping tags

Problem:
Your need to make JPA Entity with @OneToMany and @ManyToOne mapping tags.

Solution:
You have tables like this:

Table "Requests":
Field Type
ID Integer
STEP_ID Integer

Table "Steps":
Field Type
ID Integer
REQUEST_ID Integer

Table "Requests" should have in field "Step_Id" many rows from table "Steps", and table "Steps" should have in field "Requst_Id" one row from "Requests" table.

Make JPA Entities like this:

@Entity
@Table(name="REQUESTS")
public class Requests implements Serializable {

@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private long id;

@OneToMany(mappedBy="request", fetch=FetchType.EAGER)
private Set<Steps> steps = new HashSet<Steps>();


public Requests() {
}

public long getId() {
return this.id;
}

public void setId(long id) {
this.id = id;
}

public void setSteps(Set<Steps> history) {
this.steps = steps ;
}

public Set<Steps> getSteps() {
return steps;
}
}

@Entity
@Table(name="STEPS")
public class Steps implements Serializable {

@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private int id;

@ManyToOne(cascade = {CascadeType.MERGE, CascadeType.PERSIST}, fetch=FetchType.EAGER)
@JoinColumn(name = "REQUEST_ID")
private EoRequestsEntity request;

public Steps() {
}

public int getId() {
return this.id;
}

public void setRequest(Requests request) {
this.request = request;
}

public EoRequestsEntity getRequest() {
return request;
}

}


Tags "cascade" and "fetch" is required!

That's all!

среда, 24 августа 2016 г.

How to create iView for sap portal web module application

Problem:
How to create iView for sap portal web module application

Solution:

  1. Create URL iView and set link to your web module application. If you do not know thar, you can run it in your Netweaver Developer Studio: right hand mouse click on development component, choose Run on Server - choose your server and run it. You will see url in browser.
  2. In iView properties set property Fetch Mode - Server Side.



пятница, 12 августа 2016 г.

Check if your TLD is valid against its scheme

Problem:
You have an error:
Caused by: com.sap.engine.services.servlets_jsp.jspparser_api.exception.JspParseException: Error in parsing the taglib tag in the JSP page. Cannot resolve URI: [http://java.s.com/jsf/html]. Possible reason - validation failed. Check if your TLD is valid against its scheme. 


Solution:
Put in your ear (Enterprise Application) development component in file ""META-INF/application-j2ee-engine.xml"" that code:

 <application-j2ee-engine xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:noNamespaceSchemaLocation="application-j2ee-engine.xsd"> 
    <reference reference-type="weak">
    <reference-target target-type="library" provider-name="sap.com">
       tc~ui~faces
    </reference-target>
    </reference>
  </application-j2ee-engine>

End everything works!

вторник, 5 июля 2016 г.

NWDS prompt for create activity in NWDI when editing some file

To prompt for create activity in NWDI when editing some file in NWDS you should go to Window -> Preference -> Development Infrastructure -> Design Time Repository -> Dialog Settings. In that window choose prompt.

четверг, 8 октября 2015 г.

Logging and Tracing Web Service Call on SAP NetWeaver Portal

You want to see request trace whan web service was called.

You should:

  • Go to /NWA -> Log Configuration
  • Switch to Tracing Locations view
  • go to locations:

com.sap.engine.services.httpserver.HttpTraceRequest.traceHeaders
com.sap.engine.services.httpserver.HttpTraceRequest.traceRaw
com.sap.engine.services.httpserver.HttpTraceResponse.traceHeaders
com.sap.engine.services.httpserver.HttpTraceResponse.traceRaw
  • Set debug mode to all of them

пятница, 21 августа 2015 г.

How to hide in SAP Portal Header menu Back, Forward, History, Favorites, Personalize, View, Help, New Session, SAP Store, Search

Hello!

Problem:
To hide in SAP Portal Header (version 7.3) menu Back, Forward, History, Favorites, Personalize, View, Help, New Session, SAP Store, Search do this:

Solution:
Go to "Content Administration", then go and open this object:
portal_content/every_user/general/defaultAjaxframeworkContent/com.sap.portal.AFPpage

Open object AFP Masthead properties:
SAP Store - uncheck property Show Link in Masthead: Enterprise Store
New Session - uncheck property Show Link in Masthead: New Session
Search in porta header - uncheck property Enable Quick Launch

Open object AFP Widgets properties and search properties which starts with "Show" and there uncheck what you need. There will be properties: Back, Forwrard, History, Favorites, Personalize, View, Help.

понедельник, 27 июля 2015 г.

Сообщение OUTBOUND или INBOUND

Boolean outboundProperty = (Boolean) context.get(MessageContext.MESSAGE_OUTBOUND_PROPERTY);
                
                if(outboundProperty){

понедельник, 30 марта 2015 г.

How to call PI Web Service or SOAPFaultException: Server Error

Problem:
You are trying to call SAP PI - Process Integration or XI -  Exchange Infrastructure or PO - process Orchestration.

You made proxy Java Class using WSDL and NWDS, and you are trying to call it and you have error:
com.sap.engine.services.webservices.espbase.client.bindings.exceptions.SOAPFaultException: Server Error

Solution:
1. You should ask your PI developer for URL for WSDL for Web Service which you want to use. I have it like this: http://<server>:<port>/dir/wsdl?p=ic/<some id>
2. You should import WSDL in NWDS in your project using this URL.
3. Then you should generate proxy Java Classes using that WSDL.
4. It should work.

I've described how to generate proxy java classes here call Web Service Java Client (Proxy) Example.

четверг, 26 марта 2015 г.

среда, 4 марта 2015 г.

How to search checked out record in SAP MDM via MDM JAVA API

You can search, find or retrieve checked out record with MDM JAVA API in SAP MDM using property "setCheckoutSearchType()" of "Search" object. Here code example:

Code example:
    Search search = new Search;
    search.setCheckoutSearchType(Search.CheckOutSearchType.STANDARD);
    RetrieveLimitedRecordsCommand cmd = new RetrieveLimitedRecordsCommand(
    cmd.setSearch(search);
    cmd.execute();

You set search type. It can be one of the three:

Search.CheckOutSearchType.STANDARD - you will find record which was checked out as new, and you will find record which existed in MDM and which has protected version and checked out version. You will find checked out version.

Search.CheckOutSearchType.ORIGINAL - you will find original record which is not checked out. If you are searching record which checked out as new, you will not find anything, but if you are searching record which existed in MDM and it checked out, and it has protected version and checked out version, you will find protected version - it is original record.

Search.CheckOutSearchType.ALL - if you are searching record which checked out as new, then you will find it. If you are searching record which existed in MDM and it checked out and it has two versions - protected(original) and checked out version (user can change it), you will find protected version (original).

вторник, 3 марта 2015 г.

MDM Record - Checkout Status

MDM Record can be in that checkout Statuses:

Record.CheckoutStatus.UNDEFINED: -1

Record.CheckoutStatus.NONE: 0 - record is not checked out

Record.CheckoutStatus.ORIGINAL: 1 - you found original record, that means record is checked out and you found protected version of record.

Record.CheckoutStatus.MEMBER: 2 - record is checked out and you joined to checkout and you found record which is checked out, not protected version.

Record.CheckoutStatus.OWNER: 3 - record is checked out and you owner of the chekced out version, and you found checked out version, not protected version.

Record.CheckoutStatus.NON_MEMBER: 4 - record is checked out and you did not join, and you found checked out version, not protected version.

суббота, 17 января 2015 г.

Работа с JScrollPane

Для инициализации необходимы скрипты:

<script type="text/javascript" src="jquery.jscrollpane.min.js"></script>
<script type="text/javascript" src="jquery.mousewheel.js"></script>

и стили:

<link href="jquery.jscrollpane.css" rel="stylesheet"/>

Вы создаете div, указываете ему класс, задаете данному классу или div ширину и высоту и потом вызываете:

$('.myTestClass').jScrollPane();

Скроллы появятся в указанном объекте. Данный плагин ни как не влияет на высоту и ширину объекта помещаемого в него, если хотите что бы div со скроллами стал больше или меньше, изменяете с помощью скриптов ширину и высоту и вызываете снова инициализацию плагина.

среда, 14 января 2015 г.

Вызов веб сервиса с десктопа

1. Из ws навигатора вытаскиваем xml для вызова

2. Формируем xml вида:
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/">
<SOAP-ENV:Header />
<SOAP-ENV:Body>
<ns1:<"имя функции"> xmlns:ns1="нэймспэйс">
<сюда вставляем xml из ws navigator>
</ns1:start>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>

3. Либо вставляем нужные параметры в файле xml, либо вписываем метки, что бы потом считать в строку данную xml и вставить данные вместо меток, либо зашиваем в код данныю xml и уже не нужно ее читать.

4. В коде получаем xml в виде строки как указано в пункте 3
5. Вставляем нужные параметры вместо меток, если нужно.
6. Формируем SOAP Message:

MessageFactory mf = MessageFactory.newInstance();
SOAPMessage msg = mf.createMessage();

SOAPPart soappart = msg.getSOAPPart();

//создаем сообщение из string переменной xml
StreamSource preppedMsg = new StreamSource(new ByteArrayInputStream(xml.getBytes()));
soappart.setContent(preppedMsg);

// Аутентификация сообщения.
MimeHeaders headers = msg.getMimeHeaders();
String upas = _user + ":" + _pass;
String auth = "Basic " + new String(javax.xml.bind.DatatypeConverter.printBase64Binary(upas.getBytes()));
headers.addHeader("Authorization", new String(auth.getBytes()));
msg.saveChanges();