Skip to content

Commit

Permalink
Work in progress
Browse files Browse the repository at this point in the history
  • Loading branch information
VinceMacBuche committed Jul 26, 2016
1 parent a40f0f5 commit 56af789
Show file tree
Hide file tree
Showing 6 changed files with 325 additions and 27 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,9 @@ import org.joda.time.format.DateTimeFormatter
import net.liftweb.util.FieldError
import com.normation.cfclerk.domain._
import net.liftweb.http.SHtml.ChoiceHolder
import com.normation.cfclerk.domain.HashAlgoConstraint.PLAIN
import com.normation.cfclerk.domain.HashAlgoConstraint.PreHashed
import net.liftweb.util.CssSel

/**
* This field is a simple input text, without any
Expand Down Expand Up @@ -108,7 +111,6 @@ class ReadOnlyTextField(val id:String) extends DirectiveField {
def getDefaultValue = ""
}


/**
* A textarea field, with a css class
* "textareaField"
Expand Down Expand Up @@ -591,16 +593,22 @@ class PasswordField(val id: String, blankable:Boolean, algos:Seq[HashAlgoConstra
else chosenAlgo.serialize(newInput.getBytes())
}


def parseClient(s: String): Unit = {
if (null == s) _x = "" else _x = s
}
def toClient: String = if (null == _x) "" else _x

def get = _x
def get = {
logger.info("get")
logger.info(_x)
_x
}

//initialize the field
def set(x: String) = {
logger.warn("set")
logger.info(_x)
logger.info(x)
if (null == x || "" == x) _x = ""
else {
_x = x
Expand Down Expand Up @@ -634,7 +642,7 @@ class PasswordField(val id: String, blankable:Boolean, algos:Seq[HashAlgoConstra
def toForm = {
//the radio - the default value is keep
val (radioKeep, radioChange, radioBlank) = {
val radios : ChoiceHolder[String] = SHtml.radio(Seq("keep","change", "blank"), Full(currentRadio), { s =>
val radios : ChoiceHolder[String] = SHtml.radio(Seq("keep","change", "blank", "pre-hashed", "clear"), Full(currentRadio), { s =>
currentRadio = s
s match {
case "keep" => blank = false ; keepCurrent = true;
Expand All @@ -651,7 +659,7 @@ class PasswordField(val id: String, blankable:Boolean, algos:Seq[HashAlgoConstra
"name=hash" #> (if(algos.size == 1) {
Text(algos.head.prefix.toUpperCase)
} else {
SHtml.selectObj(algos.map(a => (a, a.prefix.toUpperCase))
SHtml.selectObj(algos.filterNot { x => x == PLAIN || x == PreHashed}.map(a => (a, a.prefix.toUpperCase))
, Box(currentAlgo)
, { (a:HashAlgoConstraint) => currentAlgo = Some(a) }
)
Expand All @@ -674,13 +682,44 @@ class PasswordField(val id: String, blankable:Boolean, algos:Seq[HashAlgoConstra
})
}


Full(form.apply(PasswordField.xml))

}
}

object PasswordField {

def xmlV2(id : String) = {
// Html template
def templatePath = List("templates-hidden", "components", "passwordInput")
def template() = Templates(templatePath) match {
case Empty | Failure(_,_,_) =>
sys.error(s"Template for password input configuration not found. I was looking for ${templatePath.mkString("/")}.html")
case Full(n) => n
}
def agentScheduleTemplate = chooseTemplate("password", "input", template)

val css: CssSel = ".tw-bs [id]" #> id &
".password-section [id]" #> (id+"_controller")

css(agentScheduleTemplate)

/* <div class="tw-bs" id={id} >
<div id={id+"_controller"} ng-controller="passwordController">
<div class="form-group">
<label for={id+"_current"}>Current password</label>
<input type="text" ng-model="current" class="form-control" id={id+"_current"} placeholder="No password set" readonly="" ></input>
</div>
<div class="form-group">
<label for={id+"_new"}>Current password</label>
<input type="text" ng-model="newPassword.password" ng-change="updateValue()" class="form-control" id={id+"_new"} placeholder="New password" ></input>
<input type="text" ng-model="value" class="form-control" id={id+"_new"} placeholder="New password" ></input>
{SHtml.text( "biyr", s => println(s), ("ng-model", "value")) }
</div>
</div>
</div>*/
}

val xml =
<table>
<tr><td colspan="2"><div zone="currentValue">Current password<span zone="value">(SHA256 hash): ce94806f8020be351fe3e492808a23a5b929c28a</span></div></td></tr>
Expand Down Expand Up @@ -762,16 +801,23 @@ class MasterPasswordField(val id: String, blankable:Boolean, algos:Seq[HashAlgoC
else chosenAlgo.serialize(newInput.getBytes())
}


def parseClient(s: String): Unit = {
if (null == s) _x = "" else _x = s
}
def toClient: String = if (null == _x) "" else _x

def get = _x
def get = {

logger.warn("get")
logger.info(_x)
_x
}

//initialize the field
def set(x: String) = {
logger.warn("set")
logger.info(_x)
logger.info(x)
if (null == x || "" == x) _x = ""
else {
_x = x
Expand Down Expand Up @@ -808,7 +854,6 @@ class MasterPasswordField(val id: String, blankable:Boolean, algos:Seq[HashAlgoC

val hashList = toClient :: slaves.collect { case s if(s.toClient != "") => s.toClient }


(
<span> ({algoName} hash):</span>
<ul style="overflow-x: scrollbar">{hashList.map(x => <li><pre>{x.replaceAll(":", ": ").take(60)}...</pre></li>)}</ul>
Expand All @@ -822,7 +867,7 @@ class MasterPasswordField(val id: String, blankable:Boolean, algos:Seq[HashAlgoC
import com.normation.cfclerk.domain.HashAlgoConstraint._

def name = a match {
case PLAIN => "Verbatim text"
case PLAIN |PreHashed => "Verbatim text"
case MD5 => "MD5 (Non salted)"
case SHA1 => "SHA1 (Non salted)"
case SHA256 => "SHA256 (Non salted)"
Expand Down Expand Up @@ -877,14 +922,19 @@ class MasterPasswordField(val id: String, blankable:Boolean, algos:Seq[HashAlgoC
})
}

val hashes = JsObj(algos.filterNot { x => x == PLAIN || x == PreHashed }.map(a => (a.prefix, Str(a.name))):_*)
val form2 = PasswordField.xmlV2(id) ++ Script(OnLoad( JsRaw(s"""
angular.bootstrap("#${id}", ['password']);
var scope = angular.element($$("#${id}_controller")).scope();
scope.$$apply(function(){
scope.init("${currentHash}", ${currentAlgo.map(x =>Str(x.prefix).toJsCmd).getOrElse("undefined")}, ${hashes.toJsCmd});
} );""")))

Full(form.apply(PasswordField.xml))
Full(form2)

}
}



class DerivedPasswordField(val id: String, mapping: HashAlgoConstraint.DerivedPasswordType) extends DirectiveField {
self =>
type ValueType = String
Expand All @@ -897,13 +947,11 @@ class DerivedPasswordField(val id: String, mapping: HashAlgoConstraint.DerivedPa
def validations = Nil
def setFilter = Nil


//the actual backend value like: sha1:XXXXXX
private[this] var _x: String = getDefaultValue

//the mapping between source algo and corresponding algo


/*
* Update internal value thanks to a new value from the
* master passwords field
Expand All @@ -919,7 +967,6 @@ class DerivedPasswordField(val id: String, mapping: HashAlgoConstraint.DerivedPa
_x
}


def parseClient(s: String): Unit = {
if (null == s) _x = "" else _x = s
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
/*
*************************************************************************************
* Copyright 2014 Normation SAS
*************************************************************************************
*
* This file is part of Rudder.
*
* Rudder is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* In accordance with the terms of section 7 (7. Additional Terms.) of
* the GNU General Public License version 3, the copyright holders add
* the following Additional permissions:
* Notwithstanding to the terms of section 5 (5. Conveying Modified Source
* Versions) and 6 (6. Conveying Non-Source Forms.) of the GNU General
* Public License version 3, when you create a Related Module, this
* Related Module is not considered as a part of the work and may be
* distributed under the license agreement of your choice.
* A "Related Module" means a set of sources files including their
* documentation that, without modification of the Source Code, enables
* supplementary functions or services in addition to those offered by
* the Software.
*
* Rudder is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with Rudder. If not, see <http://www.gnu.org/licenses/>.
*
*************************************************************************************
*/

//function passwordModule (passwordId) {}
var passwordModule = angular.module("password", [])
passwordModule.controller("passwordController", function($scope) {

$scope.newPassword = { password : "", hash: "md5", show: false};
$scope.action= undefined
$scope.value= undefined
$scope.current = {password : undefined, hash : "md5", show : false}
$scope.hashes = {}
$scope.init = function(current, currentHash, hashes) {
$scope.current.password=current;
$scope.hashes = hashes
$scope.current.hash = hashes[currentHash]
$scope.newPassword.hash=Object.keys(hashes)[0];

}

$scope.formType = "withHashes"
$scope.passwordForm = function(formType) {
if(formType === "withHashes") {
$scope.newPassword.hash=Object.keys($scope.hashes)[0];
} else if (formType === "clearText") {
$scope.newPassword.hash="plain"
} else if (formType === "preHashed") {
$scope.newPassword.hash="pre-hashed"
} else if (formType === "script") {
$scope.newPassword.hash="script"
}
$scope.formType=formType
}
$scope.changeAction = function(action) {
$scope.action = action
}
$scope.displayCurrent = function() {
return $scope.current.password !== undefined && $scope.action !== 'delete'
}
$scope.onChange = function() {
$("#complianceModeMessage").empty();
}

$scope.save = function() {
var run = JSON.stringify($scope.complianceMode);
$scope.callback(run);
$scope.savedValue = angular.copy($scope.complianceMode);
}

$scope.updateValue = function() {
console.log(JSON.stringify($scope.newPassword))
$scope.value = JSON.stringify($scope.newPassword)
}

$scope.isUnchanged = function(agentRun) {
return angular.equals($scope.complianceMode, $scope.savedValue);
};

$scope.displayGlobal = function() {
return $scope.complianceMode.overrides && $scope.globalRun !== undefined
}

});
58 changes: 53 additions & 5 deletions rudder-web/src/main/webapp/style/rudder-bootstrap.css
Original file line number Diff line number Diff line change
Expand Up @@ -343,10 +343,6 @@
display: table;
}

.tw-bs .control-label{
font-weight: normal;
}

#cfagentSchedule .control-label.col-sm-1 {
width:150px;
text-align:right;
Expand Down Expand Up @@ -412,4 +408,56 @@

.modal-dialog {
z-index:1050;
}
}

.tw-bs .password-section .btn{
outline: none !important;
}

.tw-bs .password-section .reveal-password:hover,.tw-bs .password-section .reveal-password:active,.tw-bs .password-section .reveal-password:focus{
background-color: #fff;
border-color: #ccc;
}
.tw-bs .password-section .btn-default.active:hover{
}
.tw-bs .password-section .input-group[class*=col-]{
padding:0 15px;
}
.tw-bs .password-section .reveal-password>span{
font-size: 16px;
padding: 2px 0;
}

.tw-bs .password-section .input-group-btn .btn{
margin-left: -3px
}
.tw-bs .password-section textarea{
resize: vertical;
border-radius: 4px !important;
}

body .tw-bs {
color: #333;
font-family: "Helvetica Neue",Helvetica,Arial,sans-serif;
font-size: 14px;
line-height: 1.42857;
}

.animate-show {
line-height: 20px;
opacity: 1;
padding: 10px;
border: 1px solid black;
background: white;
}

.animate-show.ng-hide-add, .animate-show.ng-hide-remove {
transition: all linear 0.5s;
}

.animate-show.ng-hide {
line-height: 0;
opacity: 0;
padding: 0 10px;
}

6 changes: 0 additions & 6 deletions rudder-web/src/main/webapp/style/rudder.css
Original file line number Diff line number Diff line change
Expand Up @@ -239,12 +239,6 @@ form input.radio {
vertical-align: middle;
}

form button {
width: 130px;
padding: 0.2em;
background-color: #f8f8f8;
border: 1px solid #b4b3a8;
}

button.ui-state-default {
width: 130px;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,8 @@
}

</style>

<script type="text/javascript" src="/javascript/rudder/angular/passwordForm.js" id="angular-passwordForm"></script>
</head>
</component:staticInit>

Expand Down
Loading

0 comments on commit 56af789

Please sign in to comment.