import json
import os
from kubespawner.spawner import KubeSpawner
from jhub_remote_user_authenticator.remote_user_auth import RemoteUserAuthenticator
from oauthenticator.github import GitHubOAuthenticator

class KubeFormSpawner(KubeSpawner):

  # relies on HTML5 for image datalist
  def _options_form_default(self):
    return '''
    <label for='image'>Image</label>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
    <input list="image" name="image" placeholder='repo/image:tag'>
    <datalist id="image">
      <option value="gcr.io/kubeflow-images-staging/tensorflow-1-4.1-notebook-cpu:v20180323-6e79ad3">
      <option value="gcr.io/kubeflow-images-staging/tensorflow-1-4.1-notebook-gpu:v20180323-6e79ad3">
      <option value="gcr.io/kubeflow-images-staging/tensorflow-1-5.1-notebook-cpu:v20180323-6e79ad3">
      <option value="gcr.io/kubeflow-images-staging/tensorflow-1-5.1-notebook-gpu:v20180323-6e79ad3">
      <option value="gcr.io/kubeflow-images-staging/tensorflow-1-6.1-notebook-cpu:v20180323-6e79ad3">
      <option value="gcr.io/kubeflow-images-staging/tensorflow-1-6.1-notebook-gpu:v20180323-6e79ad3">      
    </datalist>
    <br/><br/>

    <label for='cpu_guarantee'>CPU</label>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
    <input name='cpu_guarantee' placeholder='200m, 1.0, 2.5, etc'></input>
    <br/><br/>

    <label for='mem_guarantee'>Memory</label>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
    <input name='mem_guarantee' placeholder='100Mi, 1.5Gi'></input>
    <br/><br/>

    <label for='extra_resource_limits'>Extra Resource Limits</label>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
    <input name='extra_resource_limits' placeholder='{&apos;nvidia.com/gpu&apos;: &apos;3&apos;}'></input>
    <br/><br/>
    '''

  def options_from_form(self, formdata):
    options = {}
    options['image'] = formdata.get('image', [''])[0].strip()
    options['cpu_guarantee'] = formdata.get('cpu_guarantee', [''])[0].strip()
    options['mem_guarantee'] = formdata.get('mem_guarantee', [''])[0].strip()
    options['extra_resource_limits'] = formdata.get('extra_resource_limits', [''])[0].strip()
    return options

  @property
  def singleuser_image_spec(self):
    image = 'gcr.io/kubeflow/tensorflow-notebook-cpu'
    if self.user_options.get('image'):
      image = self.user_options['image']
    return image

  @property
  def cpu_guarantee(self):
    cpu = '500m'
    if self.user_options.get('cpu_guarantee'):
      cpu = self.user_options['cpu_guarantee']
    return cpu

  @property
  def mem_guarantee(self):
    mem = '1Gi'
    if self.user_options.get('mem_guarantee'):
      mem = self.user_options['mem_guarantee']
    return mem

  @property
  def extra_resource_limits(self):
    extra = ''
    if self.user_options.get('extra_resource_limits'):
      extra = json.loads(self.user_options['extra_resource_limits'])
    return extra

###################################################
### JupyterHub Options
###################################################
c.JupyterHub.ip = '0.0.0.0'
c.JupyterHub.hub_ip = '0.0.0.0'
# Don't try to cleanup servers on exit - since in general for k8s, we want
# the hub to be able to restart without losing user containers
c.JupyterHub.cleanup_servers = False
###################################################

###################################################
### Spawner Options
###################################################
c.JupyterHub.spawner_class = KubeFormSpawner
c.KubeSpawner.singleuser_image_spec = 'gcr.io/kubeflow/tensorflow-notebook'
c.KubeSpawner.cmd = 'start-singleuser.sh'
c.KubeSpawner.args = ['--allow-root']
# gpu images are very large ~15GB. need a large timeout.
c.KubeSpawner.start_timeout = 60 * 30

###################################################
### Persistent volume options
###################################################
# Using persistent storage requires a default storage class.
# TODO(jlewi): Verify this works on minikube.
# TODO(jlewi): Should we set c.KubeSpawner.singleuser_fs_gid = 1000
# see https://github.com/kubeflow/kubeflow/pull/22#issuecomment-350500944
c.KubeSpawner.user_storage_pvc_ensure = True
# How much disk space do we want?
c.KubeSpawner.user_storage_capacity = '10Gi'
c.KubeSpawner.pvc_name_template = 'claim-{username}{servername}'
c.KubeSpawner.volumes = [
  {
    'name': 'volume-{username}{servername}',
    'persistentVolumeClaim': {
      'claimName': 'claim-{username}{servername}'
    }
  }
]
c.KubeSpawner.volume_mounts = [
  {
    'mountPath': '/home/jovyan/work',
    'name': 'volume-{username}{servername}'
  }
]

@@ -571,33 +571,33 @@
 cpu:v2018032
-3-6e79ad3
+7-6bb4058
 %22%3E%0A      %3Cop
@@ -673,33 +673,33 @@
 gpu:v2018032
-3-6e79ad3
+7-6bb4058
 %22%3E%0A      %3Cop
@@ -775,33 +775,33 @@
 cpu:v2018032
-3-6e79ad3
+7-6bb4058
 %22%3E%0A      %3Cop
@@ -877,33 +877,33 @@
 gpu:v2018032
-3-6e79ad3
+7-6bb4058
 %22%3E%0A      %3Cop
@@ -983,25 +983,25 @@
 v2018032
-3-6e79ad3
+7-6bb4058
 %22%3E%0A     
@@ -1089,25 +1089,19 @@
 8032
-3-6e79ad3%22%3E      
+7-6bb4058%22%3E
 %0A   

Update tensorflow notebook release to v20180327-6bb4058 (#516)