<commit_before>package com.anchortab.snippet

import scala.xml.NodeSeq

import java.text.SimpleDateFormat
import java.util.Date

import net.liftweb._
  import http._
    import js._
      import JsCmds._
    import SHtml._
    import LiftRules._
  import common._
  import util._
    import Helpers._
  import json._
    import JsonDSL._
  import mongodb.BsonDSL._

import com.anchortab.model.{Tab, TabAppearance}

import org.bson.types.ObjectId

object requestTabId extends RequestVar[Box[String]](Empty)

object Tabs {
  val dateAndTimeFormatter = new SimpleDateFormat("MM/dd/yyyy hh:mm aa")
  val dateFormatter = new SimpleDateFormat("MM/dd/yyyy")

  def requestTab = requestTabId.is.flatMap(id => Tab.find(new ObjectId(id)))

  def statelessRewrite : RewritePF = {
    case RewriteRequest(ParsePath("manager" :: "tabs" :: "new" :: Nil, _, _, _), _, _) =>
      RewriteResponse("manager" :: "tab" :: "form" :: Nil)

    case RewriteRequest(ParsePath("manager" :: "tab" :: tabId :: "edit" :: Nil, _, _, _), _, _) =>
      requestTabId(Full(tabId))
      RewriteResponse("manager" :: "tab" :: "form" :: Nil)

    case RewriteRequest(ParsePath("manager" :: "tab" :: tabId :: "subscribers" :: Nil, _, _, _), _, _) =>
      requestTabId(Full(tabId))
      RewriteResponse("manager" :: "tab" :: "subscribers" :: Nil)

    case RewriteRequest(ParsePath("manager" :: "tab" :: tabId :: "subscribers" :: "export" :: Nil, _, _, _), _, _) =>
      requestTabId(Full(tabId))
      RewriteResponse("manager" :: "tab" :: "subscribers" :: "export" :: Nil)
  }

  def tabList = {
    val tabs = {
      for {
        session <- userSession.is
        userId = session.userId
      } yield {
        Tab.findAll("userId" -> userId)
      }
    } openOr {
      List()
    }

    def getCode(tab:Tab)() =
      Alert(tab.embedCode)

    def subscribers(tabId:ObjectId)() =
      RedirectTo("/manager/tab/" + tabId.toString + "/subscribers")

    def edit(tabId:ObjectId)() =
      RedirectTo("/manager/tab/" + tabId.toString + "/edit")

    def delete(tabId:ObjectId)() = {
      Tab.delete("_id" -> tabId)

      Alert("Tab deleted.") &
      Reload
    }

    ".empty-list" #> (tabs.isEmpty ? PassThru | ClearNodes) andThen
    ".subscriber" #> (tabs.isEmpty ? ClearNodes | PassThru) andThen
    ".subscriber" #> tabs.map { tab =>
      ".tab-name *" #> tab.name &
      ".view-count *" #> tab.stats.views &
      ".subscription-count *" #> tab.stats.submissions &
      ".get-code [onclick]" #> ajaxInvoke(getCode(tab) _) &
      ".subscribers [onclick]" #> ajaxInvoke(subscribers(tab._id) _) &
      ".edit-tab [onclick]" #> ajaxInvoke(edit(tab._id) _) &
      ".delete-tab [onclick]" #> ajaxInvoke(delete(tab._id) _)
    }
  }

  def tabForm = {
    var tabName = requestTab.map(_.name) openOr ""
    var appearanceDelay = requestTab.map(_.appearance.delay.toString) openOr ""
    var font = requestTab.map(_.appearance.font) openOr ""
    var colorScheme = requestTab.map(_.appearance.colorScheme) openOr ""
    var customText = requestTab.map(_.appearance.customText) openOr ""

    def submit = {
      {
        for {
          session <- userSession.is
        } yield {
          requestTabId.is match {
            case Full(tabId) =>
              Tab.update("_id" -> tabId, "$set" -> (
                ("name" -> tabName) ~
                ("appearance.delay" -> appearanceDelay.toInt) ~
                ("appearance.font" -> font) ~
                ("appearance.colorScheme" -> colorScheme) ~
                ("appearance.customText" -> customText)
              ))

            case _ =>
              val tab = Tab(tabName, session.userId, TabAppearance(appearanceDelay.toInt, font, colorScheme, customText))
              tab.save
          }

          RedirectTo("/manager/tabs")
        }
      } openOr {
        Alert("Something went wrong.")
      }
    }

    val bind =
      "#tab-name" #> text(tabName, tabName = _) &
      "#appearance-delay" #> selectObj[Tab.AppearanceDelayOptions.Value](
        Tab.AppearanceDelayOptions.values.toList.map(v => (v,v.toString)),
        tryo(Tab.AppearanceDelayOptions.withName(appearanceDelay)),
        selected => appearanceDelay = selected.toString
      ) &
      "#font" #> selectObj[Tab.FontOptions.Value](
        Tab.FontOptions.values.toList.map(v => (v,v.toString)),
        tryo(Tab.FontOptions.withName(font)),
        selected => font = selected.toString
      ) &
      "#color-scheme" #> selectObj[Tab.ColorSchemeOptions.Value](
        Tab.ColorSchemeOptions.values.toList.map(v => (v,v.toString)),
        tryo(Tab.ColorSchemeOptions.withName(colorScheme)),
        selected => colorScheme = selected.toString
      ) &
      ".submit" #> ajaxSubmit("Save Tab", submit _)

    "form" #> { ns:NodeSeq =>
      ajaxForm(bind(ns))
    }
  }

  def subscriberExportLink(ns:NodeSeq) = {
    val transform =
      {
        for {
          tabId <- requestTabId.is<commit_msg>Properly render custom text field on tab editor.<commit_after>package com.anchortab.snippet

import scala.xml.NodeSeq

import java.text.SimpleDateFormat
import java.util.Date

import net.liftweb._
  import http._
    import js._
      import JsCmds._
    import SHtml._
    import LiftRules._
  import common._
  import util._
    import Helpers._
  import json._
    import JsonDSL._
  import mongodb.BsonDSL._

import com.anchortab.model.{Tab, TabAppearance}

import org.bson.types.ObjectId

object requestTabId extends RequestVar[Box[String]](Empty)

object Tabs {
  val dateAndTimeFormatter = new SimpleDateFormat("MM/dd/yyyy hh:mm aa")
  val dateFormatter = new SimpleDateFormat("MM/dd/yyyy")

  def requestTab = requestTabId.is.flatMap(id => Tab.find(new ObjectId(id)))

  def statelessRewrite : RewritePF = {
    case RewriteRequest(ParsePath("manager" :: "tabs" :: "new" :: Nil, _, _, _), _, _) =>
      RewriteResponse("manager" :: "tab" :: "form" :: Nil)

    case RewriteRequest(ParsePath("manager" :: "tab" :: tabId :: "edit" :: Nil, _, _, _), _, _) =>
      requestTabId(Full(tabId))
      RewriteResponse("manager" :: "tab" :: "form" :: Nil)

    case RewriteRequest(ParsePath("manager" :: "tab" :: tabId :: "subscribers" :: Nil, _, _, _), _, _) =>
      requestTabId(Full(tabId))
      RewriteResponse("manager" :: "tab" :: "subscribers" :: Nil)

    case RewriteRequest(ParsePath("manager" :: "tab" :: tabId :: "subscribers" :: "export" :: Nil, _, _, _), _, _) =>
      requestTabId(Full(tabId))
      RewriteResponse("manager" :: "tab" :: "subscribers" :: "export" :: Nil)
  }

  def tabList = {
    val tabs = {
      for {
        session <- userSession.is
        userId = session.userId
      } yield {
        Tab.findAll("userId" -> userId)
      }
    } openOr {
      List()
    }

    def getCode(tab:Tab)() =
      Alert(tab.embedCode)

    def subscribers(tabId:ObjectId)() =
      RedirectTo("/manager/tab/" + tabId.toString + "/subscribers")

    def edit(tabId:ObjectId)() =
      RedirectTo("/manager/tab/" + tabId.toString + "/edit")

    def delete(tabId:ObjectId)() = {
      Tab.delete("_id" -> tabId)

      Alert("Tab deleted.") &
      Reload
    }

    ".empty-list" #> (tabs.isEmpty ? PassThru | ClearNodes) andThen
    ".subscriber" #> (tabs.isEmpty ? ClearNodes | PassThru) andThen
    ".subscriber" #> tabs.map { tab =>
      ".tab-name *" #> tab.name &
      ".view-count *" #> tab.stats.views &
      ".subscription-count *" #> tab.stats.submissions &
      ".get-code [onclick]" #> ajaxInvoke(getCode(tab) _) &
      ".subscribers [onclick]" #> ajaxInvoke(subscribers(tab._id) _) &
      ".edit-tab [onclick]" #> ajaxInvoke(edit(tab._id) _) &
      ".delete-tab [onclick]" #> ajaxInvoke(delete(tab._id) _)
    }
  }

  def tabForm = {
    var tabName = requestTab.map(_.name) openOr ""
    var appearanceDelay = requestTab.map(_.appearance.delay.toString) openOr ""
    var font = requestTab.map(_.appearance.font) openOr ""
    var colorScheme = requestTab.map(_.appearance.colorScheme) openOr ""
    var customText = requestTab.map(_.appearance.customText) openOr ""

    def submit = {
      {
        for {
          session <- userSession.is
        } yield {
          requestTabId.is match {
            case Full(tabId) =>
              Tab.update("_id" -> tabId, "$set" -> (
                ("name" -> tabName) ~
                ("appearance.delay" -> appearanceDelay.toInt) ~
                ("appearance.font" -> font) ~
                ("appearance.colorScheme" -> colorScheme) ~
                ("appearance.customText" -> customText)
              ))

            case _ =>
              val tab = Tab(tabName, session.userId, TabAppearance(appearanceDelay.toInt, font, colorScheme, customText))
              tab.save
          }

          RedirectTo("/manager/tabs")
        }
      } openOr {
        Alert("Something went wrong.")
      }
    }

    val bind =
      "#tab-name" #> text(tabName, tabName = _) &
      "#appearance-delay" #> selectObj[Tab.AppearanceDelayOptions.Value](
        Tab.AppearanceDelayOptions.values.toList.map(v => (v,v.toString)),
        tryo(Tab.AppearanceDelayOptions.withName(appearanceDelay)),
        selected => appearanceDelay = selected.toString
      ) &
      "#font" #> selectObj[Tab.FontOptions.Value](
        Tab.FontOptions.values.toList.map(v => (v,v.toString)),
        tryo(Tab.FontOptions.withName(font)),
        selected => font = selected.toString
      ) &
      "#color-scheme" #> selectObj[Tab.ColorSchemeOptions.Value](
        Tab.ColorSchemeOptions.values.toList.map(v => (v,v.toString)),
        tryo(Tab.ColorSchemeOptions.withName(colorScheme)),
        selected => colorScheme = selected.toString
      ) &
      "#custom-text" #> text(customText, customText = _) &
      ".submit" #> ajaxSubmit("Save Tab", submit _)

    "form" #> { ns:NodeSeq =>
      ajaxForm(bind(ns))
    }
  }

  def subscriberExportLink(ns:NodeSeq) = {
    val transform =
      {
        for {
          tabId <- requestTabId.is
{'fraction_non_alphanumeric': 0.1522567703109328, 'fraction_numerical': 0.0, 'mean_word_length': 2.5751165292219436, 'pattern_counts': {'":': 0, '<': 9, '<?xml version=': 0, '>': 84, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 2}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '4035309', 'n_tokens_mistral': 3278, 'n_tokens_neox': 3156, 'n_words': 555}