# 1st plugin - help required

**URL:** <https://forums.plex.tv/t/1st-plugin-help-required/14187>\
**Category:** Dev/API Corner\
**Tags:** plugin-dev\
**Created:** [January 14, 2012, 12:38pm UTC](https://forums.plex.tv/t/1st-plugin-help-required/14187 "2012-01-14T12:38:54Z")\
**Posts on this page:** 11\
**Page:** 1

<div class="post-metadata">

**Author:** ![mistat](https://avatars.discourse-cdn.com/v4/letter/m/ecae2f/32.png) [@mistat](https://forums.plex.tv/u/mistat)\
**Post date:** [January 14, 2012, 12:38pm UTC](https://forums.plex.tv/t/1st-plugin-help-required/14187/1 "2012-01-14T12:38:54Z")

</div>

I am trying to write a plugin to play some IPTV my ISP provides, via rtp streams.  
  
In theory this sounds pretty straight forward, however I am having huge trouble getting this off the ground. If anyone could PLEASE offer some help, I’d really appreciate it!  
  
  
  
An XML playlist is provided by my ISP, which is generated dynamically, as not everyone is entitled to the same channels - some locations (ie. Sydney) get 30 channels, where as in Adelaide, I get 5.  
  
I gather all I need to do is to parse this playlist, find the IPTV streams, and add them as videoItems. However, as the error below shows, I am not having any luck!

> [@](#):
>
> Jan 14, 2012 22:55:55 [0xb3d82000] DEBUG - File /Users/mike/Library/Application Support/Plex Media Server/Plug-ins/TPGTV.bundle/Contents/Code changed: 1326543863 =\> 1326543954.  
>   
> Jan 14, 2012 22:55:55 [0xb3d82000] DEBUG - Changed: /Users/mike/Library/Application Support/Plex Media Server/Plug-ins/TPGTV.bundle/Contents/Code  
>   
> Jan 14, 2012 22:55:55 [0xb3d82000] DEBUG - Removing directory for site configurations: /Users/mike/Library/Application Support/Plex Media Server/Plug-ins/TPGTV.bundle/Contents/Site Configurations  
>   
> Jan 14, 2012 22:55:55 [0xb3d82000] DEBUG - Stopping [com.plexapp.plugins.tpgtv].  
>   
> Jan 14, 2012 22:55:55 [0xb3d82000] DEBUG - [com.plexapp.plugins.tpgtv] Killing.  
>   
> Jan 14, 2012 22:55:55 [0xb3d82000] DEBUG - Removing directory for site configurations: /Users/mike/Library/Application Support/Plex Media Server/Plug-ins/TPGTV.bundle/Contents/Site Configurations  
>   
> Jan 14, 2012 22:55:55 [0xb3d82000] DEBUG - Perfect cache hit, we don’t need to start [com.plexapp.plugins.tpgtv] yet.  
>   
> Jan 14, 2012 22:55:55 [0xb3d82000] DEBUG - \* Added TPGTV at /video/tpgtv  
>   
> Jan 14, 2012 22:56:02 [0xb3d82000] DEBUG - Stopping file watcher for com.plexapp.plugins.tpgtv  
>   
> Jan 14, 2012 22:57:05 [0xb0699000] DEBUG - Request: GET /video/tpgtv [192.168.1.10] (1 live)  
>   
> Jan 14, 2012 22:57:05 [0xb0699000] DEBUG - Plug-in com.plexapp.plugins.tpgtv has been used 41 times.  
>   
> Jan 14, 2012 22:57:05 [0xb0699000] DEBUG - Starting file watcher for com.plexapp.plugins.tpgtv  
>   
> Jan 14, 2012 22:57:05 [0xb0699000] DEBUG - Spawned plug-in com.plexapp.plugins.tpgtv with PID 26409  
>   
> Jan 14, 2012 22:57:05 [0xb0699000] DEBUG - [com.plexapp.plugins.tpgtv] Sent command: GET /:/prefixes  
>   
> Jan 14, 2012 22:57:05 [0xb3d82000] DEBUG - File /Users/mike/Library/Application Support/Plex Media Server/Plug-ins/TPGTV.bundle/Contents/Code changed: 1326543954 =\> 1326544014.  
>   
> Jan 14, 2012 22:57:05 [0xb3d82000] DEBUG - File /Users/mike/Library/Application Support/Plex Media Server/Plug-ins/TPGTV.bundle/Contents/Code/ **init**.py changed: 1326543954 =\> 1326544014.  
>   
> Jan 14, 2012 22:57:05 [0xb3d82000] DEBUG - Changed: /Users/mike/Library/Application Support/Plex Media Server/Plug-ins/TPGTV.bundle/Contents/Code  
>   
> Jan 14, 2012 22:57:05 [0xb3d82000] DEBUG - Changed: /Users/mike/Library/Application Support/Plex Media Server/Plug-ins/TPGTV.bundle/Contents/Code/ **init**.py  
>   
> Jan 14, 2012 22:57:05 [0xb3d82000] DEBUG - Removing directory for site configurations: /Users/mike/Library/Application Support/Plex Media Server/Plug-ins/TPGTV.bundle/Contents/Site Configurations  
>   
> Jan 14, 2012 22:57:05 [0xb3d82000] DEBUG - Stopping [com.plexapp.plugins.tpgtv].  
>   
> Jan 14, 2012 22:57:05 [0xb3d82000] DEBUG - [com.plexapp.plugins.tpgtv] Killing.  
>   
> Jan 14, 2012 22:57:05 [0xb0699000] ERROR - Error reading from plug-in [com.plexapp.plugins.tpgtv], we’re killing it (got: ‘’).  
>   
> Jan 14, 2012 22:57:05 [0xb3d82000] DEBUG - Removing directory for site configurations: /Users/mike/Library/Application Support/Plex Media Server/Plug-ins/TPGTV.bundle/Contents/Site Configurations  
>   
> Jan 14, 2012 22:57:05 [0xb3d82000] DEBUG - Starting file watcher for com.plexapp.plugins.tpgtv  
>   
> Jan 14, 2012 22:57:05 [0xb3d82000] DEBUG - Spawned plug-in com.plexapp.plugins.tpgtv with PID 26410  
>   
> Jan 14, 2012 22:57:05 [0xb3d82000] DEBUG - [com.plexapp.plugins.tpgtv] Sent command: GET /:/prefixes  
>   
> Jan 14, 2012 22:57:06 [0xb071b000] DEBUG - Request: GET /system/messaging/clear\_events/com.plexapp.plugins.tpgtv [127.0.0.1] (2 live)  
>   
> Jan 14, 2012 22:57:06 [0xb071b000] DEBUG - [com.plexapp.system] Sending command over HTTP (GET): /system/messaging/clear\_events/com.plexapp.plugins.tpgtv  
>   
> Jan 14, 2012 22:57:06 [0xb071b000] DEBUG - HTTP request to: [http://127.0.0.1:49170/system/messaging/clear\_events/com.plexapp.plugins.tpgtv](http://127.0.0.1:49170/system/messaging/clear_events/com.plexapp.plugins.tpgtv)  
>   
> Jan 14, 2012 22:57:06 [0xb3d82000] DEBUG - [com.plexapp.plugins.tpgtv] Plug-in running on port 55588.  
>   
> Jan 14, 2012 22:57:06 [0xb3d82000] DEBUG - \* Plug-in handles prefix: /video/tpgtv  
>   
> Jan 14, 2012 22:57:06 [0xb3d82000] DEBUG - Read configuration for [com.plexapp.plugins.tpgtv], had 1 prefixes  
>   
> Jan 14, 2012 22:57:06 [0xb3d82000] DEBUG - Updating [com.plexapp.plugins.tpgtv] in the database, it has changed.  
>   
> Jan 14, 2012 22:57:06 [0xb0699000] DEBUG - Stopping [com.plexapp.plugins.tpgtv].  
>   
> Jan 14, 2012 22:57:06 [0xb0699000] DEBUG - [com.plexapp.plugins.tpgtv] Killing.  
>   
> Jan 14, 2012 22:57:06 [0xb0699000] ERROR - Error received reading configuration for com.plexapp.plugins.tpgtv  
>   
> Jan 14, 2012 22:57:06 [0xb0699000] DEBUG - Stopping [com.plexapp.plugins.tpgtv].

  
  
I've used the basic kick start, and simply edited the \_\_init\_\_.py file to add some custom features, like attempting to parse a XML document, and append menu options based upon the results.  
But whenever I enable my for loop as below, I'm met with all the errors show above.  
  

```auto

VIDEO_PREFIX = "/video/tpgtv"<br />
<br />
NAME = L('Title')<br />
<br />
# make sure to replace artwork with what you want<br />
# these filenames reference the example files in<br />
# the Contents/Resources/ folder in the bundle<br />
ART = 'art-default.jpg'<br />
ICON = 'icon-default.png'<br />
<br />
####################################################################################################<br />
<br />
def Start():<br />
<br />
    ## make this plugin show up in the 'Video' section<br />
    ## in Plex. The L() function pulls the string out of the strings<br />
    ## file in the Contents/Strings/ folder in the bundle<br />
    ## see also:<br />
    ## http://dev.plexapp.com/docs/mod_Plugin.html<br />
    ## http://dev.plexapp.com/docs/Bundle.html#the-strings-directory<br />
    Plugin.AddPrefixHandler(VIDEO_PREFIX, VideoMainMenu, NAME, ICON, ART)<br />
<br />
    Plugin.AddViewGroup("InfoList", viewMode="InfoList", mediaType="items")<br />
    Plugin.AddViewGroup("List", viewMode="List", mediaType="items")<br />
<br />
    ## set some defaults so that you don't have to<br />
    ## pass these parameters to these object types<br />
    ## every single time<br />
    ## see also:<br />
    ## http://dev.plexapp.com/docs/Objects.html<br />
    MediaContainer.title1 = NAME<br />
    MediaContainer.viewGroup = "List"<br />
    MediaContainer.art = R(ART)<br />
    DirectoryItem.thumb = R(ICON)<br />
    VideoItem.thumb = R(ICON)<br />
<br />
    HTTP.CacheTime = CACHE_1HOUR<br />
<br />
<br />
<br />
<br />
#### the rest of these are user created functions and<br />
#### are not reserved by the plugin framework.<br />
#### see: http://dev.plexapp.com/docs/Functions.html for<br />
#### a list of reserved functions above<br />
<br />
<br />
<br />
#<br />
# Example main menu referenced in the Start() method<br />
# for the 'Video' prefix handler<br />
#<br />
<br />
def VideoMainMenu():<br />
<br />
<br />
    # Container acting sort of like a folder on<br />
    # a file system containing other things like<br />
    # "sub-folders", videos, music, etc<br />
    # see:<br />
    # http://dev.plexapp.com/docs/Objects.html#MediaContainer<br />
    dir = MediaContainer(viewGroup="InfoList")<br />
<br />
<br />
    # see:<br />
    # http://dev.plexapp.com/docs/Objects.html#DirectoryItem<br />
    # http://dev.plexapp.com/docs/Objects.html#function-objects<br />
    dir.Append(<br />
        Function(<br />
            DirectoryItem(<br />
                CallbackExample,<br />
                "directory item title",<br />
                subtitle="subtitle",<br />
                summary="clicking on me will call CallbackExample",<br />
                thumb=R(ICON),<br />
                art=R(ART)<br />
            )<br />
        )<br />
    )<br />
<br />
    for iptvStream in XML.ElementFromURL('http://www.tpg.com.au/iptv/playlist.php',isHTML=true,errors='ignore').xpath('/a:playlist/a:trackList/a:track'):<br />
        dir.Append(<br />
            Function(<br />
                DirectoryItem(<br />
                    CallbackExample,<br />
                    "1234",<br />
                    subtitle="subtitle",<br />
                    summary="clicking on me will call CallbackExample",<br />
                    thumb=R(ICON),<br />
                    art=R(ART)<br />
                )<br />
            )<br />
        )<br />
<br />
<br />
<br />
<br />
    # ... and then return the container<br />
    return dir<br />
<br />
def CallbackExample(sender):<br />
<br />
    ## you might want to try making me return a MediaContainer<br />
    ## containing a list of DirectoryItems to see what happens =)<br />
<br />
    return MessageContainer(<br />
        "Not implemented",<br />
        "In real life, you'll make more than one callback,
and you'll do something useful.
sender.itemTitle=%s" % sender.itemTitle<br />
    )

```

  
  
An example of the XML document is:  

```auto

<?xml version="1.0" encoding="UTF-8"?><br />
<playlist version="1" xmlns="http://xspf.org/ns/0/"><br />
<trackList><br />
	<track><br />
		<location>rtp://@al-jazeera.iptv.tpg.com.au:1234</location><br />
		<title>Al Jazeera</title><br />
	</track><br />
	<track><br />
		<location>rtp://@bloomberg.iptv.tpg.com.au:1234</location><br />
		<title>Bloomberg</title><br />
	</track><br />
	<track><br />
		<location>rtp://@cnai.iptv.tpg.com.au:1234</location><br />
		<title>Channel News Asia</title><br />
	</track><br />
	<track><br />
		<location>rtp://@phoenix-info-news.iptv.tpg.com.au:1234</location><br />
		<title>Phoenix InfoNews</title><br />
	</track><br />
	<track><br />
		<location>rtp://@tv5-monde.iptv.tpg.com.au:1234</location><br />
		<title>TV5 Monde</title><br />
	</track><br />
	<track><br />
		<location>rtp://@playboy.iptv.tpg.com.au:1234</location><br />
		<title>Playboy TV</title><br />
	</track><br />
</trackList><br />
</playlist><br />
 <br />

```

---

<div class="post-metadata">

**Author:** ![jam](https://sea1.discourse-cdn.com/plex/user_avatar/forums.plex.tv/jam/32/186050_2.png) [@jam](https://forums.plex.tv/u/jam)\
**Post date:** [January 14, 2012, 1:24pm UTC](https://forums.plex.tv/t/1st-plugin-help-required/14187/2 "2012-01-14T13:24:01Z")

</div>

Hey Mike!  
  
  
  
A plug-in failing to start like that indicates a syntax error in the code. If you check the individual plug-in log file in the “~/Library/Logs/PMS Plugin Logs” folder, this should provide more information.

---

<div class="post-metadata">

**Author:** ![mistat](https://avatars.discourse-cdn.com/v4/letter/m/ecae2f/32.png) [@mistat](https://forums.plex.tv/u/mistat)\
**Post date:** [January 14, 2012, 1:53pm UTC](https://forums.plex.tv/t/1st-plugin-help-required/14187/3 "2012-01-14T13:53:03Z")

</div>

> [@](#):
>
> Hey Mike!  
>   
> A plug-in failing to start like that indicates a syntax error in the code. If you check the individual plug-in log file in the "~/Library/Logs/PMS Plugin Logs" folder, this should provide more information.

  
  
Hey Jam, thanks for pointing me to the plugin log - I had looked for that but couldnt find it anywhere!  
Unfortunately the output doesnt appear to be very helpful  

> [@](#):
>
> 2012-01-14 22:57:06,528 (-53eaad40) : DEBUG (core:169) - Using the standard security policy  
>   
> 2012-01-14 22:57:06,528 (-53eaad40) : DEBUG (core:202) - Starting runtime component.  
>   
> 2012-01-14 22:57:06,535 (-53eaad40) : DEBUG (core:204) - Starting caching component.  
>   
> 2012-01-14 22:57:06,535 (-53eaad40) : DEBUG (core:206) - Starting data component.  
>   
> 2012-01-14 22:57:06,536 (-53eaad40) : DEBUG (core:208) - Starting networking component.  
>   
> 2012-01-14 22:57:06,536 (-53eaad40) : DEBUG (networking:392) - Setting the default network timeout to 20.0  
>   
> 2012-01-14 22:57:06,537 (-53eaad40) : DEBUG (networking:248) - Loaded HTTP cookies  
>   
> 2012-01-14 22:57:06,583 (-53eaad40) : DEBUG (core:210) - Starting localization component.  
>   
> 2012-01-14 22:57:06,583 (-53eaad40) : INFO (localization:406) - Setting the default locale to en-us  
>   
> 2012-01-14 22:57:06,585 (-53eaad40) : DEBUG (localization:424) - Loaded en strings  
>   
> 2012-01-14 22:57:06,585 (-53eaad40) : DEBUG (localization:440) - Unable to find en-us strings  
>   
> 2012-01-14 22:57:06,585 (-53eaad40) : DEBUG (core:212) - Starting messaging component.  
>   
> 2012-01-14 22:57:06,586 (-53eaad40) : DEBUG (runtime:979) - Created a thread named ‘get\_server\_info’  
>   
> 2012-01-14 22:57:06,587 (-4f8e5000) : DEBUG (networking:115) - Requesting ‘[http://127.0.0.1:32400](http://127.0.0.1:32400)’  
>   
> 2012-01-14 22:57:06,588 (-4f967000) : DEBUG (networking:115) - Requesting ‘[http://127.0.0.1:32400/system/messaging/clear\_events/com.plexapp.plugins.tpgtv](http://127.0.0.1:32400/system/messaging/clear_events/com.plexapp.plugins.tpgtv)’  
>   
> 2012-01-14 22:57:06,804 (-53eaad40) : DEBUG (runtime:979) - Created a thread named ‘load\_all\_services’  
>   
> 2012-01-14 22:57:06,805 (-4f967000) : DEBUG (networking:115) - Requesting ‘[http://127.0.0.1:32400/:/plugins/com.plexapp.system/messaging/function/X0J1bmRsZVNlcnZpY2U6QWxsU2VydmljZXM\_/Y2VyZWFsMQoxCmxpc3QKMApyMAo\_/Y2VyZWFsMQoxCmRpY3QKMApyMAo\_](http://127.0.0.1:32400/:/plugins/com.plexapp.system/messaging/function/X0J1bmRsZVNlcnZpY2U6QWxsU2VydmljZXM_/Y2VyZWFsMQoxCmxpc3QKMApyMAo_/Y2VyZWFsMQoxCmRpY3QKMApyMAo_)’  
>   
> 2012-01-14 22:57:06,809 (-53eaad40) : DEBUG (accessor:68) - Creating a new model access point for provider com.plexapp.plugins.tpgtv in namespace ‘metadata’  
>   
> 2012-01-14 22:57:06,809 (-4f8e5000) : DEBUG (core:283) - Machine identifier is 61c7b493172edff87f896f050cf04c9aebbcfedf  
>   
> 2012-01-14 22:57:06,810 (-53eaad40) : DEBUG (classes:9) - Generating class for ‘Album’ model in namespace ‘metadata’ with access point ‘com.plexapp.plugins.tpgtv’  
>   
> 2012-01-14 22:57:06,812 (-53eaad40) : DEBUG (classes:9) - Generating class for ‘Episode’ model in namespace ‘metadata’ with access point ‘com.plexapp.plugins.tpgtv’  
>   
> 2012-01-14 22:57:06,813 (-53eaad40) : DEBUG (classes:9) - Generating class for ‘TV\_Show’ model in namespace ‘metadata’ with access point ‘com.plexapp.plugins.tpgtv’  
>   
> 2012-01-14 22:57:06,811 (-4f863000) : DEBUG (prefskit:218) - Loaded preferences from DefaultPrefs.json  
>   
> 2012-01-14 22:57:06,814 (-53eaad40) : DEBUG (classes:9) - Generating class for ‘Artist’ model in namespace ‘metadata’ with access point ‘com.plexapp.plugins.tpgtv’  
>   
> 2012-01-14 22:57:06,812 (-4f8e5000) : DEBUG (core:284) - Server version is 0.9.3.4-397e914  
>   
> 2012-01-14 22:57:06,815 (-53eaad40) : DEBUG (classes:9) - Generating class for ‘Track’ model in namespace ‘metadata’ with access point ‘com.plexapp.plugins.tpgtv’  
>   
> 2012-01-14 22:57:06,815 (-53eaad40) : DEBUG (classes:9) - Generating class for ‘Movie’ model in namespace ‘metadata’ with access point ‘com.plexapp.plugins.tpgtv’  
>   
> 2012-01-14 22:57:06,816 (-53eaad40) : DEBUG (classes:9) - Generating class for ‘Photo’ model in namespace ‘metadata’ with access point ‘com.plexapp.plugins.tpgtv’  
>   
> 2012-01-14 22:57:06,817 (-53eaad40) : DEBUG (classes:9) - Generating class for ‘VideoClip’ model in namespace ‘metadata’ with access point ‘com.plexapp.plugins.tpgtv’  
>   
> 2012-01-14 22:57:06,819 (-53eaad40) : DEBUG (classes:9) - Generating class for ‘Person’ model in namespace ‘metadata’ with access point ‘com.plexapp.plugins.tpgtv’  
>   
> 2012-01-14 22:57:06,820 (-53eaad40) : DEBUG (classes:9) - Generating class for ‘Role’ model in namespace ‘metadata’ with access point ‘com.plexapp.plugins.tpgtv’  
>   
> 2012-01-14 22:57:06,820 (-53eaad40) : DEBUG (classes:9) - Generating class for ‘Season’ model in namespace ‘metadata’ with access point ‘com.plexapp.plugins.tpgtv’  
>   
> 2012-01-14 22:57:06,822 (-53eaad40) : DEBUG (classes:9) - Generating class for ‘PhotoAlbum’ model in namespace ‘metadata’ with access point ‘com.plexapp.plugins.tpgtv’  
>   
> 2012-01-14 22:57:06,825 (-53eaad40) : DEBUG (core:258) - Finished starting framework core  
>   
> 2012-01-14 22:57:06,826 (-53eaad40) : DEBUG (core:301) - Loading plug-in code  
>   
> 2012-01-14 22:57:06,849 (-53eaad40) : DEBUG (core:443) - Running pre-flight checks  
>   
> 2012-01-14 22:57:06,851 (-53eaad40) : DEBUG (runtime:473) - Adding a prefix handler for ‘TPGTV’ (‘/video/tpgtv’)  
>   
> 2012-01-14 22:57:06,851 (-53eaad40) : INFO (core:450) - Started plug-in  
>   
> 2012-01-14 22:57:06,852 (-53eaad40) : DEBUG (socketinterface:137) - Starting socket server  
>   
> 2012-01-14 22:57:06,854 (-53eaad40) : DEBUG (runtime:979) - Created a thread named ‘start’  
>   
> 2012-01-14 22:57:06,854 (-53eaad40) : INFO (socketinterface:161) - Socket server started on port 55588  
>   
> 2012-01-14 22:57:06,855 (-53eaad40) : INFO (pipeinterface:28) - Entering run loop  
>   
> 2012-01-14 22:57:06,858 (-53eaad40) : DEBUG (runtime:528) - Handling request GET /:/prefixes  
>   
> 2012-01-14 22:57:06,862 (-53eaad40) : DEBUG (runtime:678) - Response: 200

---

<div class="post-metadata">

**Author:** ![mikedm139](https://sea1.discourse-cdn.com/plex/user_avatar/forums.plex.tv/mikedm139/32/96909_2.png) [@mikedm139](https://forums.plex.tv/u/mikedm139)\
**Post date:** [January 14, 2012, 5:57pm UTC](https://forums.plex.tv/t/1st-plugin-help-required/14187/4 "2012-01-14T17:57:26Z")

</div>

I just want to clarify, does the plugin show up in the client? Are you able to open it?  
  
  
  
Also, I would change this line

```auto

for iptvStream in XML.ElementFromURL('http://www.tpg.com.au/iptv/playlist.php',isHTML=true,errors='ignore').xpath('/a:playlist/a:trackList/a:track'):

```

  
to  

```auto

for iptvStream in XML.ElementFromURL('http://www.tpg.com.au/iptv/playlist.php',errors='ignore').xpath('//track'):

```

  
The "isHTML" flag indicates that you're trying to parse HTML using the XML parser instead of the HTML parser, which you're not since you have nice clean XML. The change to the xpath just cleans it up and I don't think the "a:" tags are necessary.

---

<div class="post-metadata">

**Author:** ![mistat](https://avatars.discourse-cdn.com/v4/letter/m/ecae2f/32.png) [@mistat](https://forums.plex.tv/u/mistat)\
**Post date:** [January 14, 2012, 11:03pm UTC](https://forums.plex.tv/t/1st-plugin-help-required/14187/5 "2012-01-14T23:03:48Z")

</div>

> [@](#):
>
> I just want to clarify, does the plugin show up in the client? Are you able to open it?  
>   
> Also, I would change this line  
> 
> ```auto
> 
> for iptvStream in XML.ElementFromURL('http://www.tpg.com.au/iptv/playlist.php',isHTML=true,errors='ignore').xpath('/a:playlist/a:trackList/a:track'):
> 
> ```
> 
>   
> to  
> 
> ```auto
> 
> for iptvStream in XML.ElementFromURL('http://www.tpg.com.au/iptv/playlist.php',errors='ignore').xpath('//track'):
> 
> ```
> 
>   
> The "isHTML" flag indicates that you're trying to parse HTML using the XML parser instead of the HTML parser, which you're not since you have nice clean XML. The change to the xpath just cleans it up and I don't think the "a:" tags are necessary.

  
  
  
Hey Mikedm139, the plugin shows correctly, but would not launch.  
I've made the changes as you suggested and its now launching! Thankyou!  
  
I need to revise my XPATH iteration as it is not picking up any tracks, with //track or with /playlist/trackList/track. I think this may have something to do with the xmlns="http://xspf.org/ns/0/" name space - I'm not sure how to parse the XML correctly.  
  
  

```auto

2012-01-15 09:24:01,772 (-4fa6b000) : DEBUG (prefskit:218) - Loaded preferences from DefaultPrefs.json<br />
2012-01-15 09:24:01,774 (-4faed000) : DEBUG (runtime:528) - Handling request GET /video/tpgtv<br />
2012-01-15 09:24:01,776 (-4faed000) : DEBUG (runtime:575) - Found prefix handler matching /video/tpgtv<br />
2012-01-15 09:24:01,776 (-4faed000) : INFO ( __init__ :50) - VideoMainMenu initiated<br />
2012-01-15 09:24:01,777 (-4fa6b000) : DEBUG (prefskit:320) - Loaded the user preferences for com.plexapp.plugins.tpgtv<br />
2012-01-15 09:24:01,779 (-4fa6b000) : DEBUG (prefskit:353) - Saved the user preferences<br />
2012-01-15 09:24:01,780 (-4faed000) : DEBUG (networking:111) - Fetching 'http://www.tpg.com.au/iptv/playlist.php' from the HTTP cache<br />
2012-01-15 09:24:01,786 (-4faed000) : DEBUG (runtime:678) - Response: 200

```

---

<div class="post-metadata">

**Author:** ![sander1](https://avatars.discourse-cdn.com/v4/letter/s/4bbf92/32.png) [@sander1](https://forums.plex.tv/u/sander1)\
**Post date:** [January 14, 2012, 11:26pm UTC](https://forums.plex.tv/t/1st-plugin-help-required/14187/6 "2012-01-14T23:26:08Z")

</div>

The playlist.php file shows up empty for me … :huh:   
  
Anyway, you can declare the namespace(s) as a dict and then prefix the elements in your xpath that need it with the right key:

```auto

NAMESPACES = {'a':'http://xspf.org/ns/0/'}<br />
<br />
# ...<br />
<br />
for iptvStream in XML.ElementFromURL('http://www.tpg.com.au/iptv/playlist.php', errors='ignore').xpath('//a:track', namespaces=NAMESPACES):<br />
  # ...<br />

```

---

<div class="post-metadata">

**Author:** ![mistat](https://avatars.discourse-cdn.com/v4/letter/m/ecae2f/32.png) [@mistat](https://forums.plex.tv/u/mistat)\
**Post date:** [January 15, 2012, 12:44am UTC](https://forums.plex.tv/t/1st-plugin-help-required/14187/7 "2012-01-15T00:44:21Z")

</div>

> [@](#):
>
> The playlist.php file shows up empty for me ... :huh:

  
  
I assume that's because it's a dynamically generated file, and the contents vary on the IPTV content available to you - and given TPG IPTV is for tpg.com.au customers only, the file may not generate content if your not on a TPG internet connection.  
  

> [@](#):
>
> Anyway, you can declare the namespace(s) as a dict and then prefix the elements in your xpath that need it with the right key:  
>   
> 
> ```auto
> 
> NAMESPACES = {'a':'http://xspf.org/ns/0/'}<br />
> <br />
> # ...<br />
> <br />
> for iptvStream in XML.ElementFromURL('http://www.tpg.com.au/iptv/playlist.php', errors='ignore').xpath('//a:track', namespaces=NAMESPACES):<br />
> # ...<br />
> 
> ```

  
  
  
HOTDAMN! IT WORKED! I now see 6 new menu items labelled "1234".  
  
Now I just need to get the actual URL and provide the RTP stream, and I should be laughing!  
  
Thanks for the ongoing help everyone!

---

<div class="post-metadata">

**Author:** ![mistat](https://avatars.discourse-cdn.com/v4/letter/m/ecae2f/32.png) [@mistat](https://forums.plex.tv/u/mistat)\
**Post date:** [January 16, 2012, 9:07pm UTC](https://forums.plex.tv/t/1st-plugin-help-required/14187/8 "2012-01-16T21:07:46Z")

</div>

hey i’m going to bump this as I’m stuck further. Basically - I cannot open a web stream of the rtp content!  
  
I just get a “Error while opening file” error!  
  
I’m so close i can taste victory! Please Help!  
  
  
  
My Code:

```auto

<br />
VIDEO_PREFIX = "/video/tpgtv"<br />
NAME = L('Title')<br />
ART = 'art-default.jpg'<br />
ICON = 'icon-default.png'<br />
NAMESPACES = {'a':'http://xspf.org/ns/0/'}<br />
<br />
####################################################################################################<br />
def Start():<br />
<br />
    Plugin.AddPrefixHandler(VIDEO_PREFIX, VideoMainMenu, NAME, ICON, ART)<br />
<br />
    Plugin.AddViewGroup("InfoList", viewMode="InfoList", mediaType="items")<br />
    Plugin.AddViewGroup("List", viewMode="List", mediaType="items")<br />
<br />
    MediaContainer.title1 = NAME<br />
    MediaContainer.viewGroup = "List"<br />
    MediaContainer.art = R(ART)<br />
    DirectoryItem.thumb = R(ICON)<br />
    VideoItem.thumb = R(ICON)<br />
    <br />
    HTTP.CacheTime = CACHE_1HOUR<br />
<br />
<br />
<br />
<br />
<br />
<br />
####################################################################################################<br />
def VideoMainMenu():<br />
<br />
<br />
    dir = MediaContainer(viewGroup="InfoList")<br />
<br />
<br />
    i=0<br />
    xmlData = XML.ElementFromURL('http://www.tpg.com.au/iptv/playlist.php',errors='ignore')<br />
    for iptvStream in xmlData.xpath('//a:track', namespaces=NAMESPACES):<br />
        url = iptvStream.xpath('//a:location', namespaces=NAMESPACES)*.text<br />
        title = iptvStream.xpath('//a:title', namespaces=NAMESPACES)*.text<br />
        Log("Found stream " + title + " (" + url + ")")<br />
<br />
        thumbTitle = title.lower().replace(" ","")<br />
        thumbTitle = thumbTitle.replace("channelnewsasia", "newsasia")<br />
        thumb = 'http://www.tpg.com.au/iptv/img/logo_' + thumbTitle + '_s.gif'<br />
        Log("Thumb: " + thumb)<br />
<br />
<br />
        dir.Append(<br />
            WebVideoItem(<br />
                url,<br />
                title=title,<br />
                subtitle="Click to open this stream!",<br />
                summary="Uh..",<br />
                thumb=thumb<br />
            )<br />
        ) i = i + 1<br />
<br />
 <br />
<br />
<br />
<br />
<br />
    return dir

```

  
  
My Log:  

```auto

2012-01-17 07:20:00,935 (-4faed000) : DEBUG (networking:111) - Fetching 'http://www.tpg.com.au/iptv/playlist.php' from the HTTP cache<br />
2012-01-17 07:20:00,937 (-4faed000) : INFO ( __init__ :42) - Found stream Al Jazeera (rtp://@al-jazeera.iptv.tpg.com.au:1234)<br />
2012-01-17 07:20:00,938 (-4faed000) : INFO ( __init__ :48) - Thumb: http://www.tpg.com.au/iptv/img/logo_aljazeera_s.gif<br />
2012-01-17 07:20:00,939 (-4faed000) : INFO ( __init__ :42) - Found stream Bloomberg (rtp://@bloomberg.iptv.tpg.com.au:1234)<br />
2012-01-17 07:20:00,939 (-4faed000) : INFO ( __init__ :48) - Thumb: http://www.tpg.com.au/iptv/img/logo_bloomberg_s.gif<br />
2012-01-17 07:20:00,940 (-4faed000) : INFO ( __init__ :42) - Found stream Channel News Asia (rtp://@cnai.iptv.tpg.com.au:1234)<br />
2012-01-17 07:20:00,941 (-4faed000) : INFO ( __init__ :48) - Thumb: http://www.tpg.com.au/iptv/img/logo_newsasia_s.gif4<br />
2012-01-17 07:20:00,941 (-4faed000) : INFO ( __init__ :42) - Found stream Phoenix InfoNews (rtp://@phoenix-info-news.iptv.tpg.com.au:1234)<br />
2012-01-17 07:20:00,942 (-4faed000) : INFO ( __init__ :48) - Thumb: http://www.tpg.com.au/iptv/img/logo_phoenixinfonews_s.gif<br />
2012-01-17 07:20:00,943 (-4faed000) : INFO ( __init__ :42) - Found stream TV5 Monde (rtp://@tv5-monde.iptv.tpg.com.au:1234)<br />
2012-01-17 07:20:00,943 (-4faed000) : INFO ( __init__ :48) - Thumb: http://www.tpg.com.au/iptv/img/logo_tv5monde_s.gif<br />
2012-01-17 07:20:00,944 (-4faed000) : INFO ( __init__ :42) - Found stream Playboy TV (rtp://@playboy.iptv.tpg.com.au:1234)<br />
2012-01-17 07:20:00,945 (-4faed000) : INFO ( __init__ :48) - Thumb: http://www.tpg.com.au/iptv/img/logo_playboytv_s.gif<br />
2012-01-17 07:20:00,948 (-4faed000) : DEBUG (runtime:678) - Response: 200

```

  
  
  
PMSLog  

```auto

Jan 17, 2012 07:31:29 [0xb0b2b000] DEBUG - [com.plexapp.plugins.tpgtv] Plug-in running on port 64532.<br />
Jan 17, 2012 07:31:29 [0xb0b2b000] DEBUG - * Plug-in handles prefix: /video/tpgtv<br />
Jan 17, 2012 07:31:29 [0xb0b2b000] DEBUG - Read configuration for [com.plexapp.plugins.tpgtv], had 1 prefixes<br />
Jan 17, 2012 07:31:29 [0xb0b2b000] DEBUG - [com.plexapp.plugins.tpgtv] Sending command over HTTP (GET): /video/tpgtv<br />
Jan 17, 2012 07:31:30 [0xb0b2b000] DEBUG - HTTP request to: http://127.0.0.1:64532/video/tpgtv<br />
Jan 17, 2012 07:31:30 [0xb0b2b000] DEBUG - [com.plexapp.plugins.tpgtv] HTTP reply status 200, with 1846 bytes of content.<br />
Jan 17, 2012 07:31:32 [0xb0c2f000] DEBUG - Request: GET /video/:/webkit?url=rtp%3A%2F%2F%40al-jazeera.iptv.tpg.com.au%3A1234&prefix=/video/tpgtv [127.0.0.1] (1 live)<br />
Jan 17, 2012 07:31:32 [0xb0c2f000] DEBUG - * prefix => /video/tpgtv<br />
Jan 17, 2012 07:31:32 [0xb0c2f000] DEBUG - Found corresponding plug-in: /Users/mike/Library/Application Support/Plex Media Server/Plug-in Support/Data/com.plexapp.plugins.tpgtv

```

---

<div class="post-metadata">

**Author:** ![mistat](https://avatars.discourse-cdn.com/v4/letter/m/ecae2f/32.png) [@mistat](https://forums.plex.tv/u/mistat)\
**Post date:** [January 17, 2012, 12:56pm UTC](https://forums.plex.tv/t/1st-plugin-help-required/14187/9 "2012-01-17T12:56:21Z")

</div>

Thanks for your help everyone. I’ve discovered if I use UDP:// rather than RTP:// the stream works. Its very choppy, but now I get audio & video.  
  
  
  
Ultimately I’d like to see native RTP streams handled in Plex, but alas, I guess there’s not the demand for it, and Elan and the other gods are busy bringing us this awesome media center without looking at spending too much on small requests from the community.   
  
It works. Im happy!  
  
[http://wiki.plexapp.com/index.php/TPGTV](http://wiki.plexapp.com/index.php/TPGTV)

---

<div class="post-metadata">

**Author:** ![Cigaras](https://sea1.discourse-cdn.com/plex/user_avatar/forums.plex.tv/cigaras/32/163056_2.png) [@Cigaras](https://forums.plex.tv/u/Cigaras)\
**Post date:** [October 8, 2013, 7:56am UTC](https://forums.plex.tv/t/1st-plugin-help-required/14187/10 "2013-10-08T07:56:10Z")

</div>

Could someone explain me what this addon is supposed to do? It fetches channels &nbsp;from TPG and shows them in Plex Media Server, so what next? How to view them on Plex Player?

---

<div class="post-metadata">

**Author:** ![system](https://global.discourse-cdn.com/plex/original/3X/2/a/2acb9765406f63293d357b4ec509ec39aa28f2ad.png) [@system](https://forums.plex.tv/u/system)\
**Post date:** [December 20, 2019, 9:36pm UTC](https://forums.plex.tv/t/1st-plugin-help-required/14187/11 "2019-12-20T21:36:19Z")

</div>

This topic was automatically closed 90 days after the last reply. New replies are no longer allowed.
