1

Code in native PHP:

$href = phpUri::parse($target_url)->join($href);

Code I tried in CI which is not working:

$CI->load->library('Phpuri', array($target_url));
$href = $CI->phpuri->parse($target_url);
$href = $CI->phpuri->join($href);

You can see the phpUri native library here. I've just changed the case of class name rest is same to make it work in CI. I am using this in another library so using the CI instance.

SilentAssassin
  • 468
  • 1
  • 9
  • 27

1 Answers1

1

CodeIgniter's pattern is a singleton. The phpUri uses static calls. There is a great difference between them that I suggest you to familiarize with.

The point here is that phpUri uses the static call parse which is requested from the class, not the object itself and as CodeIgniter is a singleton, it's an object with sub-objects (said that for simplicity, read more about that). With that being said, the reason why this doesn't work is that phpUri does not behave like an object and only produces(returns) objects after the static call:

$href = phpUri::parse($target_url)->join($href);

can be simplified to:

$parsed = phpUri::parse($target_url);
$href = $parsed->join($href);

the first line is the static call which returns an object to $parsed variable and then you can play with that.

In singleton, you can't make a 'classes parent' by defining a class as an objects attribute. That's why to use this library, you should rewrite all the static calls first.

But it is much easier to write an abstraction layer library in CodeIgniter that uses static calls in it's object's non-static methods:

class MyPhpUri {
    function parse($target_url) {
        return phpUri::parse($target_url);        
    }
}

Then in your library

$CI =& get_instance();
$CI->load->library('MyPhpUri');
$href = $CI->myphpuri->parse($target_url)->join($var);

That is what an abstract class is - the one that gives you an interface.

Sergey Telshevsky
  • 12,077
  • 6
  • 55
  • 78
  • Should I use this link http://stackoverflow.com/questions/11128290/library-as-singleton-in-codeigniter to solve my issue ? – SilentAssassin Feb 05 '13 at 09:41
  • The first code block in the **question** is the way I would go! See my updated answer – Sergey Telshevsky Feb 05 '13 at 09:43
  • ^ Okay actually the `$target_url` will not be available to the library. So can I load the library like this : `$this->load->library('MyPhpUri', $target_url);` to make it available there ? Also I am writing this in another library so I will use `$CI` instead of `$this`. That won't be an issue, right ? – SilentAssassin Feb 05 '13 at 09:50
  • I have updated the code above and no, you don't need to pass the `$target_url` straight when loading a library, it's not effective as you may want to work with different URL's in one session and it will get complicated. Pass it to the `parse()` method. – Sergey Telshevsky Feb 05 '13 at 09:57
  • I am getting this warning : `Missing argument 1 for Phpuri::__construct(), called in C:\wamp\www\codeigniter\system\core\Loader.php on line 1099 and defined` And this error: `Maximum function nesting level of '100' reached, aborting! in C:\wamp\www\codeigniter\application\libraries\Phpuri.php on line 19` Line 19 is `return phpUri::parse($target_url);` – SilentAssassin Feb 05 '13 at 10:05
  • You have named your library `phpuri` that is a conflict with the `phpUri` library, name it `myphpuri` for instance, that's why you get the second error and most likely the first one too. – Sergey Telshevsky Feb 05 '13 at 10:10
  • I think you misunderstood me. I am improvising the phpUri library to act as a CI library. See here http://pastebin.com/UgNSRtUJ – SilentAssassin Feb 05 '13 at 10:19
  • I understand that, that's why on lines 18-20 you try to call not the original `phpUri` class, but the class which this method is located in - the codeigniter library class as it has the same name as the original. Basically PHP interprets this as `self::parse()` which causes endless recursion, not `phpUri::parse()`. To fix - rename your library to anything else. – Sergey Telshevsky Feb 05 '13 at 10:23
  • So I've to create two classes and it is working. One is phpUri and another is Myphpuri. Can't this be done in the phpUri class itself using some other approach ? – SilentAssassin Feb 05 '13 at 12:55
  • @SilentAssassin rewrite every static method in the class as I suggested in my answer, but this will not allow you to update the `phpUri` class by simply replacing it's class file if it updates. I may suggest another solution, rename the original class to something else and use this in your library – Sergey Telshevsky Feb 05 '13 at 15:04
  • I've to use the class anyhow so I've used it with the original name and it works. This is another question I am having: http://stackoverflow.com/questions/14681304/run-controller-methods-in-background-codeigniter-windows – SilentAssassin Feb 06 '13 at 08:16