I have a very simple CodeIngiter code in a controller to call a WebService exposed on a .NET application. Both Codeigniter and the .NET applications run under IIS / Windows.
The issue I have is that I get a "Method not allowed" when I try to call a method from that Web Service.
Here is my controller in CodeIgniter
<?php
defined('BASEPATH') OR exit('No direct script access allowed');
class TestWS extends CI_Controller {
public function index()
{
$client = new SoapClient(
"https://localhost/myWebApp/services/MyWebServices.Samples.asmx?wsdl",
array(
"trace" => 1,
"location" => "https://localhost/",
'exceptions' => 1,
"stream_context" => stream_context_create(
array(
'ssl' => array(
'verify_peer' => false,
'verify_peer_name' => false,
)
)
)
)
);
$client->GetSamples_sessionless(null, null, "myuser", "mypassword");
var_dump($client);
}
}
and what I get is
An uncaught Exception was encountered
Type: SoapFault
Message: Method Not Allowed
I can also browse to the WSDL and see it properly
Code crashes in the GetSamples (whether sessionless or not with this issue).
This may be an IIS permission, not sure
What am I missing?
Thanks!
Related
I'm trying to write a Laravel test case where I need to make an HTTP Post Request to an external API. But my $this->postJson() keeps giving me an exception. Here's an excerpt from my code:
namespace Tests\Feature;
use Tests\TestCase;
class PurchaseTest extends TestCase
{
protected function setUp(): void
{
parent::setUp();
}
public function testPurchasePolicy()
{
$response = $this->postJson('https://apitest.cybersource.com/flex/v1/',['cardNumber'=>'4111111111111111']);
print_r($response->json());
$response->assertOk();
}
}
This gives the result:
Array
(
[message] =>
[exception] => Symfony\Component\HttpKernel\Exception\NotFoundHttpException
[file] => /var/www/projects/local/vendor/laravel/framework/src/Illuminate/Routing/AbstractRouteCollection.php
[line] => 43
[trace] => Array
(
[0] => Array
(
[file] => /var/www/projects/local/vendor/laravel/framework/src/Illuminate/Routing/RouteCollection.php
[line] => 162
[function] => handleMatchedRoute
[class] => Illuminate\Routing\AbstractRouteCollection
/// --> then a stack trace of laravel code that failed
)
You won't be able to fully run my code because it requires some API keys with cybersource. But i'm pretty sure my code is failing because I'm not properly telling Laravel that the API i want to access is an external resource.
What is the idiomatic way for Laravel to connect with an external URL?
You have to use an HTTP Client.
Install guzzle with composer:
composer require guzzlehttp/guzzle
Then:
For laravel 7.x and above, use the HTTP Client facade:
use Illuminate\Support\Facades\Http;
$response = Http::get('http://test.com');
Check the laravel documentation about HTTP Client usage.
For laravel 6.x or below, use guzzle like:
$client = new \GuzzleHttp\Client();
$res = $client->request('GET', 'https://api.github.com/user', [
'auth' => ['user', 'pass']
]);
check the Guzzle docs.
In new Laravel
use Illuminate\Support\Facades\Http;
$response = Http::get('http://theusoffice.com/');
and if you need to use https and having issues with it try
$response = Http::withOptions(['verify' => false])->get('https://www.google.com/');
I hope some of you guys can help me I'm new to SOAP API and having rough time.
I'm using my client's database (database using soap api), my admin side or backend is laravel. I'm having some trouble with storing data using soap api to my client's database. I've already connected my laravel to their database. I was able to store data using the wsdl URL from my client using SOAPUI software.
Basically, I created a TestController in Laravel
<?php
namespace App\Http\Controllers;
use SoapWrapper;
use Illuminate\Http\Request;
use App\Helpers\SoapHelper;
class TestController extends Controller
{
private $client;
public function index()
{
$result = $this->client->CreateMember(
[
'CreateMemberRequest' =>
array(
'siteId' => '1',
'membership' =>
array(
'membershipId' => '',
'termId' => '',
'memberNumber' => '',
),
'personal' =>
array(
'title' => '',
'firstName' => '',
'middleName' => '',
'lastName' => '',
'preferredName' => '',
),
),
]
);
}
}
The siteId is "1" but when I input it the error shows "SOAP-ERROR: Encoding: object has no 'siteId' property"
NEEDS SOME HELP
On my website I use cron job on cpanel.
I have this code below in the construct area of controller but it stops the cpanel cron job from working.
if (!$this->input->is_cli_request()) {
show_error('Direct access is not allowed');
}
Question Do I need the code above. if I use my cpanel cron job? I just want to make it more secure.
<?php
class Cron extends CI_Controller {
public function __construct() {
parent::__construct();
if (!$this->input->is_cli_request()) {
show_error('Direct access is not allowed');
}
$this->load->library('email');
$this->load->model('members_model');
}
public function message()
{
$admin_email = $this->config->item('email_host');
$admin_email_pass = $this->config->item('email_password');
$companyname = 'Riwaka';
$config = array(
'protocol' => 'smtp',
'smtp_host' => 'ssl://mail.yourdomain.co.nz',
'smtp_port' => 465,
'smtp_user' => $admin_email,
'smtp_pass' => $admin_email_pass,
'mailtype' => 'html',
'charset' => 'iso-8859-1'
);
$this->email->initialize($config);
$members = $this->members_model->get_approved_members_for_cron_job();
if ($members) {
foreach ($members as $member) {
if ($member['approved'] == '1' && $member['approved_email_sent'] == '0')
{
$this->email->set_newline("\r\n");
$this->email->clear();
$this->email->from($admin_email, 'Admin');
$this->email->to($member['email']);
$this->email->subject($companyname .' Account Approved');
$this->email->message('test');
$update = array(
'approved_email_sent' => '1',
);
$this->members_model->update_approve_email_send($member['email'], $update);
$this->email->send();
}
}
}
}
}
To prevent direct access from a webpage:
you need to add this line
/* deny direct call from web browser */
if (isset($_SERVER['REMOTE_ADDR'])) die('Permission denied.');
with CI 3.0 you can
Make your cron-jobs inaccessible from being loaded in the URL by
checking the return value of is_cli().
is_cli() returns TRUE if the application is run through the command line and FALSE if not.
as by my comment, the cpanel cron job pattern is:
/usr/bin/php /var/www/website/public_html/cli.php controller method
,
see docs here
related post
Solved now. CodeIgniter Cron Job through Cpanel
It seem to be a issue from path I had used. On cpanel before I had
php --silent http://mysubdomain.mydomain.co.nz/cron/message
That was not working proper if I wanted to use this code to prevent access
if (!$this->input->is_cli_request()) {
show_error('Direct access is not allowed');
}
So now I changed to
php-cli /home/myusername/public_html/mysubdomain/index.php Cron message
All works fine now
I'm currently using the Omnipay extension library to simply handle my Rabobank omnikassa transactions. Now when i use the code below i get a selection of all credit card methods but IDEAL and MINITIX are not listed on the page. Not sure what i'm doing wrong, first time i'm using an external library to handle my payments. Rabobank Omnikassa should display all available payment methods on default.
The Library:
https://github.com/thephpleague/omnipay-rabobank
My Code: iDealController
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Http\Requests;
use Omnipay\Omnipay;
class iDealController extends Controller
{
public function loadPage()
{
$sOrderId = 'WEB' . time(); // This should be unique - Order id
$sTransactionReference = $sOrderId . date('His'); // This should be unique - Identifier of transaction
$amount = 10.00;
$gateway = Omnipay::create('Rabobank');
$request = $gateway->purchase(array(
'testMode' => true,
'merchantId' => '002020000000001',
'keyVersion' => '1',
'secretKey' => '002020000000001_KEY1',
'amount' => $amount,
'returnUrl' => 'http://localhost:8888/',
'automaticResponseUrl' => 'http://localhost:8888/',
'currency' => 'EUR',
'transactionReference' => $sTransactionReference,
'orderId' => $sOrderId,
'customerLanguage' => "EN"
)
);
$data = $request->getData();
$response = $request->sendData($data);
if ($response->isSuccessful()) {
// payment was successful: update database
print_r($response);
} elseif ($response->isRedirect()) {
// redirect to offsite payment gateway
$response->redirect();
} else {
// payment failed: display message to customer
echo $response->getMessage();
}
return view('omnikassa');
}
}
When i add: 'PaymentMethod' => 'IDEAL' to the request array it gives the following error: Technical problem : code=03 message=None of the merchant's payment means is compliant with the transaction context. So definitely something is going wrong.
Sept 2 update:
This has become a very difficult puzzle to solve. Setting up a basic auth, which is all that I want, should involve very few steps. I have done many tests, adding and removing code, reviewing the cake manual, reading tutorials and going step by step through the cakePHP 1.3 application development cookbook by Mariano Iglesias - good book. http://goo.gl/93BGw
But the problem I'm still facing is that the app controller is the only place the 'allowed' actions work. In individual controllers the parent:beforeFilter doesn't get recognized and I'm redirected back to the users login page.
Any help with this is really appreciated. What I'm wondering is how I might debug this type of problem. Are there any other configuration settings I should look at, like 'prefix routing'?
=======================
Sept 1 update:
After a lot of testing what appears to be the issue is that the 'before:filter' in individual controllers isn't being recognized. Example in the post controller:
public function beforeFilter() {
parent::beforeFilter();
$this->Auth->allow = array('edit');
}
Has anyone had this happen before? I've referred to the cakePHP manual as well as many online articles and tutorials and it doesn't make any sense to me. I've even tried to build a simple application with just the users and post controller and still, the before:filter settings in each controller aren't being recognized.
=======================
Original question.
I am using the Cakephp auth component to manage an admin section. This is using version 1.3.11
The problem I'm having is that even with allowed actions in each controller, I'm being redirected to the user login page.
Here is what's in the app controller:
class AppController extends Controller {
var $components = array(
'Auth' => array(
'authorize' => 'controller'
),
'Session',
'RequestHandler'
);
public function isAuthorized() {
return true;
}
function beforeFilter(){
$this->Auth->authorize = 'controller';
$this->Auth->fields = array('username' => 'username', 'password' => 'password');
$this->Auth->loginAction = array('controller' => 'users', 'action' => 'login');
$this->Auth->authError = 'Please login to view that page ';
$this->Auth->loginError =' The user name or password you entered did not work, please try again ' ;
$this->Auth->allow('display');
$this->Auth->loginAction = array('controller' => 'users', 'action' => 'login');
$this->Auth->logoutRedirect = array('controller' => 'users', 'action' => 'logout');
$this->Auth->loginRedirect = array('controller' => 'pages', 'action' => 'display', 'home');
}
This is what's in the users controller:
class UsersController extends AppController {
var $name = 'Users';
function beforeFilter() {
parent::beforeFilter();
$this->Auth->allow = array('add');
}
This is what's in the posts controller:
class PostsController extends AppController {
var $name = 'Posts';
var $components = array('Session','RequestHandler', 'Email');
public function beforeFilter() {
parent::beforeFilter();
$this->Auth->allow = array('edit');
}
What I do find is that after I've logged in I'm able to access the home page, as expected. Then when I go to the logout the session isn't entirely destroyed so I can go back to the 'admin' section.
I did try using $this-session('destroy'); in the logout action, but when I did the allowed actions didn't work again.
Does this make sense? Shouldn't allowed actions be independent of a current session?
Thanks, Paul
Make sure you are not using requestAction in any of your elements or views, make sure that the actions called by requestAction are allowed too.... this should fix it.
For the one when you logout and I can still access admin section: the logout() should have $this->redirect($this->Auth->logout()); It should clear the Auth session data.
Here's what I suggest for the beforeFilter() in appcontroller:
function beforeFilter(){
$this->Auth->loginRedirect = array('controller' => 'users', 'action' => 'dashboard');
}
and for the pages controller: $this->Auth->allow('display', 'view');