// Example Program: T_KLSSNHOP
// Description:
//  This is a test program to illustrate how to call the CTI_Run()
//  subprocedure to perform the AltPay Session Service operation for
//  Klarna for a Hosted Order Page (HOP).
//
//  To achieve this, generate a unique ID with CTI_NextUniqueId(), and
//  then write records to CTIWSHDR and to CTIWSAHDR, as well as any line
//  item data to CTIWSITM. Then, call CTI_Run() passing in your unique
//  ID as well as the other parameters shown.
//
//  CTI_Run() will return *On if no error was encountered, or *Off
//  if an error occurred. If an error occurred, you should look at
//  the fields in ErrorDS to retrieve information about the error.
//
//  Otherwise, you can perform a CHAIN against the CTIWSRSP and
//  CTIWSARSP physical files, and retrieve the result fields.
Ctl-Opt ActGrp(*Caller) BndDir('CTIBND') Option(*NoDebugIO);
Dcl-F CTIWSHDR Disk(*Ext) Keyed Qualified Usage(*Input:*Output);
Dcl-F CTIWSAHDR Disk(*Ext) Keyed Qualified Usage(*Input:*Output);
Dcl-F CTIWSITM Disk(*Ext) Keyed Qualified Usage(*Input:*Output);
Dcl-F CTIWSRSP Disk(*Ext) Keyed Qualified Usage(*Input);
Dcl-F CTIWSARSP Disk(*Ext) Keyed Qualified Usage(*Input);
Dcl-Ds HDR ExtName('CTIWSHDR':*Output) Qualified End-Ds;
Dcl-Ds AHDR ExtName('CTIWSAHDR':*Output) Qualified End-Ds;
Dcl-Ds ITM ExtName('CTIWSITM':*Output) Qualified End-Ds;
Dcl-Ds RSP ExtName('CTIWSRSP':*Input) Qualified End-Ds;
Dcl-Ds ARSP ExtName('CTIWSARSP':*Input) Qualified End-Ds;
/COPY QRPGLECPY,CTICB
// This is included for demo output purposes.
Dcl-Pr WriteToJobLog Int(10) Extproc('Qp0zLprintf');
  pString Pointer Value Options(*String);
End-Pr;
Dcl-C NewLine x'15';
// This stores the unique ID for this API call
Dcl-S UniqueId Like(CTI_UniqueId_t) Inz;
// This holds any error information returned by the API call
Dcl-Ds ErrorDS LikeDS(CTI_ErrorDS_t) Inz(*LikeDS);
// Modify this field to use your merchant ID
Dcl-S MerchantId Like(CTI_MerchantId_t) Inz('ikrengel');
reset ErrorDS;
// Each API call requires a unique ID
UniqueId = CTI_NextUniqueId();
// CTIWSHDR and CTIWSAHDR need to be populated with transaction data.
//  CTIWSAHDR will be populated with Klarna AltPay-specific data
clear HDR;
HDR.UID = UniqueId;
HDR.CRTDT = %Timestamp();
HDR.MCHID = MerchantId;
HDR.MCHREFCD = 'MYREFCD134';
HDR.PTCUR = 'USD';
HDR.PTGNDAMT = '127.52';
// US only
HDR.PTTAXAMT = '0.00';
//HDR.PTDSCAMT = '0.00';
HDR.BTCNTRY = 'US';
// Unsure if required
HDR.BTPSTCD = '56001';
// US only
HDR.BTSTT = 'MN';
clear AHDR;
AHDR.UID = UniqueId;
AHDR.SSNRUN = CTI_TRUE;
AHDR.APPMTTYP = CTI_ALTPAYTYPE_KLARNA;
// current valid values: HOP, inline
// can use the constants
//  - CTI_PAYFLOWMODE_HOP
//  - CTI_PAYFLOWMODE_INLINE
AHDR.SSNPFMODE = CTI_PAYFLOWMODE_HOP;
// Set URL to redirect to if customer cancels Klarna payment
AHDR.SSNCNLURL = 'https://www.example.com/cancel';
// Set URL to redirect to if Klarna payment fails
AHDR.SSNFAILURL = 'https://www.example.com/failure';
// current valid values: pay_now, pay_later, pay_over_time
// can use the constants
//  - CTI_PAYMETHOD_NOW
//  - CTI_PAYMETHOD_LATER
//  - CTI_PAYMETHOD_OVER_TIME
AHDR.SSNPMTMD = CTI_PAYMETHOD_NOW;
// For initial session creation, this should be set to
//  CTI_SESSIONTYPE_CREATE - for a session update, instead
//  use CTI_SESSIONTYPE_UPDATE
AHDR.SSNTYPE = CTI_SESSIONTYPE_CREATE;
// Need to include ?auth-token= at end of URL
AHDR.SSNSCSURL =
  'https://www.example.com?auth-token=';
write CTIWSHDR.CTIWSHDRR HDR;
write CTIWSAHDR.CTIWSAHDRR AHDR;
// CTIWSITM needs to be populated with one or more line items
clear ITM;
ITM.PID = UniqueId;
ITM.UID = CTI_NextUniqueId();
ITM.CRTDT = %Timestamp();
ITM.PRDNAM = 'File Cabinet';
ITM.UNTPRC = '59.95';
ITM.QTY = 10;
// non-US only
ITM.TAXAMT = '49.96';
ITM.TOTAMT = '648.96';
write CTIWSITM.CTIWSITMR ITM;
// optional: add a coupon as a line item
//clear ITM;
//ITM.PID = UniqueId;
//ITM.UID = CTI_NextUniqueId();
//ITM.CRTDT = %Timestamp();
//ITM.PRDCD = 'coupon';
//ITM.PRDNAM = '';
//ITM.PRDSKU = '';
//ITM.UNTPRC = '10.00';
//ITM.QTY = 1;
//write CTIWSITM.CTIWSITMR ITM;
if not CTI_Run( UniqueId : ErrorDS : *Omit : *Omit : MerchantId );
  // If CTI_Run() returns *Off then an error occurred.
  // You should check ErrorDS subfields for info:
  //  ErrorDS.Subproc = Name of CTI subprocedure that threw error
  //  ErrorDS.MessageId = Message ID of the error message
  //  ErrorDS.Message = Error message description
  //  ErrorDS.LogFile = Path to a log file created in the IFS that can
  //   be used for troubleshooting. Log files are generated
  //   automatically whenever an error occurs. You can also force log
  //   files to generate by modifying the value of the LOGALL field in
  //   CTICFGCER for the provided Merchant ID.
  //  ErrorDS.Source =
  //    - CTI_SOURCE_INTERNAL is a general product error.
  //      This could be due to issues with input data, or the
  //      inability to access physical files, etc.
  //
  //    - CTI_SOURCE_TRANSMIT is a product error that specifically
  //      occurred during HTTPS communication with the CyberSource
  //      webservice. This could be due to issues with your network
  //      configuration, proxy setup, internet connection, etc.
  //
  //    - CTI_SOURCE_REMOTE is an error message provided by CyberSource.
  WriteToJobLog( 'Error Message Id: ' + ErrorDS.MessageId + NewLine );
  WriteToJobLog( 'Error Message: ' + ErrorDS.Message + NewLine );
  WriteToJobLog( 'Error Source: ' + ErrorDS.Source + NewLine );
  // All error information is also written to the file CTIERR.
else;
  // If CTI_Run() returned *On the request was successful. You can
  //  access the results in the CTIWSRSP file using the same UniqueID
  //  that was used to create the request record in CTIWSRSP.
  chain UniqueId CTIWSRSP.CTIWSRSPR RSP;
  if %Found(CTIWSRSP);
    chain UniqueId CTIWSARSP.CTIWSARSPR ARSP;
    if not %Found(CTIWSARSP);
      // TODO: error, no AP data in response
    endif;
    // For this sample code we're writing the response data to the job
    //  log, but generally you would extract the data and pass it into
    //  your own data tables. The CTIWSHDR, CTIWSAHDR, CTIWSMDD,
    //  CTIWSARSP, and CTIWSRSP files should not be used for long-term
    //  data storage and should instead be considered short-term
    //  transactional files.
    WriteToJobLog( 'SSNAMT: ' + ARSP.SSNAMT + NewLine );
    WriteToJobLog( 'SSNMCHURL: ' + ARSP.SSNMCHURL + NewLine );
    WriteToJobLog( 'SSNPRCTID: ' + ARSP.SSNPRCTID + NewLine );
    WriteToJobLog( 'SSNRSNCD: ' + %Char(ARSP.SSNRSNCD) + NewLine );
    WriteToJobLog( 'SSNRECID: ' + ARSP.SSNRECID + NewLine );
    WriteToJobLog( 'SSNRSPCD: ' + %Char(ARSP.SSNRSPCD) + NewLine );
    WriteToJobLog( 'SSNSTS: ' + ARSP.SSNSTS + NewLine );
    WriteToJobLog( 'SSNPRCTK: ' + ARSP.SSNPRCTK + NewLine );
    WriteToJobLog( 'REQID: ' + RSP.REQID + NewLine );
    WriteToJobLog( 'REQTK: ' + RSP.REQTK + NewLine );
    WriteToJobLog( 'DCN: ' + RSP.DCN + NewLine );
    WriteToJobLog( 'RSNCD: ' + %Char(RSP.RSNCD) + NewLine );
  endif;
endif;
// Write unique ID to job log for easy reference
WriteToJobLog( 'T_KLSSNHOP Unique ID: ' + %Char(UniqueId) + NewLine );
*INLR = *On;
return;