Commit cb8b5c32 authored by Dmitriy Zaporozhets's avatar Dmitriy Zaporozhets

Merge branch 'ce-into-ee' into 'master'

CE into EE

See merge request !303
parents 45349abd 96a3f0e0
Style/AccessModifierIndentation:
Description: Check indentation of private/protected visibility modifiers.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#indent-public-private-protected'
Enabled: true
Style/AccessorMethodName:
Description: Check the naming of accessor methods for get_/set_.
Enabled: false
Style/Alias:
Description: 'Use alias_method instead of alias.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#alias-method'
Enabled: true
Style/AlignArray:
Description: >-
Align the elements of an array literal if they span more than
one line.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#align-multiline-arrays'
Enabled: true
Style/AlignHash:
Description: >-
Align the elements of a hash literal if they span more than
one line.
Enabled: true
Style/AlignParameters:
Description: >-
Align the parameters of a method call if they span more
than one line.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-double-indent'
Enabled: false
Style/AndOr:
Description: 'Use &&/|| instead of and/or.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-and-or-or'
Enabled: false
Style/ArrayJoin:
Description: 'Use Array#join instead of Array#*.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#array-join'
Enabled: false
Style/AsciiComments:
Description: 'Use only ascii symbols in comments.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#english-comments'
Enabled: true
Style/AsciiIdentifiers:
Description: 'Use only ascii symbols in identifiers.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#english-identifiers'
Enabled: true
Style/Attr:
Description: 'Checks for uses of Module#attr.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#attr'
Enabled: false
Style/BeginBlock:
Description: 'Avoid the use of BEGIN blocks.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-BEGIN-blocks'
Enabled: true
Style/BarePercentLiterals:
Description: 'Checks if usage of %() or %Q() matches configuration.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#percent-q-shorthand'
Enabled: false
Style/BlockComments:
Description: 'Do not use block comments.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-block-comments'
Enabled: false
Style/BlockEndNewline:
Description: 'Put end statement of multiline block on its own line.'
Enabled: true
Style/Blocks:
Description: >-
Avoid using {...} for multi-line blocks (multiline chaining is
always ugly).
Prefer {...} over do...end for single-line blocks.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#single-line-blocks'
Enabled: true
Style/BracesAroundHashParameters:
Description: 'Enforce braces style around hash parameters.'
Enabled: false
Style/CaseEquality:
Description: 'Avoid explicit use of the case equality operator(===).'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-case-equality'
Enabled: false
Style/CaseIndentation:
Description: 'Indentation of when in a case/when/[else/]end.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#indent-when-to-case'
Enabled: true
Style/CharacterLiteral:
Description: 'Checks for uses of character literals.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-character-literals'
Enabled: true
Style/ClassAndModuleCamelCase:
Description: 'Use CamelCase for classes and modules.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#camelcase-classes'
Enabled: true
Style/ClassAndModuleChildren:
Description: 'Checks style of children classes and modules.'
Enabled: false
Style/ClassCheck:
Description: 'Enforces consistent use of `Object#is_a?` or `Object#kind_of?`.'
Enabled: false
Style/ClassMethods:
Description: 'Use self when defining module/class methods.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#def-self-singletons'
Enabled: false
Style/ClassVars:
Description: 'Avoid the use of class variables.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-class-vars'
Enabled: true
Style/ColonMethodCall:
Description: 'Do not use :: for method call.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#double-colons'
Enabled: false
Style/CommentAnnotation:
Description: >-
Checks formatting of special comments
(TODO, FIXME, OPTIMIZE, HACK, REVIEW).
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#annotate-keywords'
Enabled: false
Style/CommentIndentation:
Description: 'Indentation of comments.'
Enabled: true
Style/ConstantName:
Description: 'Constants should use SCREAMING_SNAKE_CASE.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#screaming-snake-case'
Enabled: true
Style/DefWithParentheses:
Description: 'Use def with parentheses when there are arguments.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#method-parens'
Enabled: false
Style/DeprecatedHashMethods:
Description: 'Checks for use of deprecated Hash methods.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#hash-key'
Enabled: false
Style/Documentation:
Description: 'Document classes and non-namespace modules.'
Enabled: false
Style/DotPosition:
Description: 'Checks the position of the dot in multi-line method calls.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#consistent-multi-line-chains'
Enabled: false
Style/DoubleNegation:
Description: 'Checks for uses of double negation (!!).'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-bang-bang'
Enabled: false
Style/EachWithObject:
Description: 'Prefer `each_with_object` over `inject` or `reduce`.'
Enabled: false
Style/ElseAlignment:
Description: 'Align elses and elsifs correctly.'
Enabled: true
Style/EmptyElse:
Description: 'Avoid empty else-clauses.'
Enabled: false
Style/EmptyLineBetweenDefs:
Description: 'Use empty lines between defs.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#empty-lines-between-methods'
Enabled: false
Style/EmptyLines:
Description: "Don't use several empty lines in a row."
Enabled: false
Style/EmptyLinesAroundAccessModifier:
Description: "Keep blank lines around access modifiers."
Enabled: false
Style/EmptyLinesAroundBlockBody:
Description: "Keeps track of empty lines around block bodies."
Enabled: false
Style/EmptyLinesAroundClassBody:
Description: "Keeps track of empty lines around class bodies."
Enabled: false
Style/EmptyLinesAroundModuleBody:
Description: "Keeps track of empty lines around module bodies."
Enabled: false
Style/EmptyLinesAroundMethodBody:
Description: "Keeps track of empty lines around method bodies."
Enabled: false
Style/EmptyLiteral:
Description: 'Prefer literals to Array.new/Hash.new/String.new.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#literal-array-hash'
Enabled: false
Style/EndBlock:
Description: 'Avoid the use of END blocks.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-END-blocks'
Enabled: false
Style/EndOfLine:
Description: 'Use Unix-style line endings.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#crlf'
Enabled: false
Style/EvenOdd:
Description: 'Favor the use of Fixnum#even? && Fixnum#odd?'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#predicate-methods'
Enabled: false
Style/FileName:
Description: 'Use snake_case for source file names.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#snake-case-files'
Enabled: false
Style/FlipFlop:
Description: 'Checks for flip flops'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-flip-flops'
Enabled: false
Style/For:
Description: 'Checks use of for or each in multiline loops.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-for-loops'
Enabled: false
Style/FormatString:
Description: 'Enforce the use of Kernel#sprintf, Kernel#format or String#%.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#sprintf'
Enabled: false
Style/GlobalVars:
Description: 'Do not introduce global variables.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#instance-vars'
Enabled: false
Style/GuardClause:
Description: 'Check for conditionals that can be replaced with guard clauses'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-nested-conditionals'
Enabled: false
Style/HashSyntax:
Description: >-
Prefer Ruby 1.9 hash syntax { a: 1, b: 2 } over 1.8 syntax
{ :a => 1, :b => 2 }.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#hash-literals'
Enabled: true
Style/IfUnlessModifier:
Description: >-
Favor modifier if/unless usage when you have a
single-line body.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#if-as-a-modifier'
Enabled: false
Style/IfWithSemicolon:
Description: 'Do not use if x; .... Use the ternary operator instead.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-semicolon-ifs'
Enabled: false
Style/IndentationConsistency:
Description: 'Keep indentation straight.'
Enabled: true
Style/IndentationWidth:
Description: 'Use 2 spaces for indentation.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#spaces-indentation'
Enabled: true
Style/IndentArray:
Description: >-
Checks the indentation of the first element in an array
literal.
Enabled: false
Style/IndentHash:
Description: 'Checks the indentation of the first key in a hash literal.'
Enabled: false
Style/InfiniteLoop:
Description: 'Use Kernel#loop for infinite loops.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#infinite-loop'
Enabled: false
Style/Lambda:
Description: 'Use the new lambda literal syntax for single-line blocks.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#lambda-multi-line'
Enabled: false
Style/LambdaCall:
Description: 'Use lambda.call(...) instead of lambda.(...).'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#proc-call'
Enabled: false
Style/LeadingCommentSpace:
Description: 'Comments should start with a space.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#hash-space'
Enabled: false
Style/LineEndConcatenation:
Description: >-
Use \ instead of + or << to concatenate two string literals at
line end.
Enabled: false
Style/MethodCallParentheses:
Description: 'Do not use parentheses for method calls with no arguments.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-args-no-parens'
Enabled: false
Style/MethodDefParentheses:
Description: >-
Checks if the method definitions have or don't have
parentheses.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#method-parens'
Enabled: false
Style/MethodName:
Description: 'Use the configured style when naming methods.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#snake-case-symbols-methods-vars'
Enabled: false
Style/ModuleFunction:
Description: 'Checks for usage of `extend self` in modules.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#module-function'
Enabled: false
Style/MultilineBlockChain:
Description: 'Avoid multi-line chains of blocks.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#single-line-blocks'
Enabled: false
Style/MultilineBlockLayout:
Description: 'Ensures newlines after multiline block do statements.'
Enabled: false
Style/MultilineIfThen:
Description: 'Do not use then for multi-line if/unless.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-then'
Enabled: false
Style/MultilineOperationIndentation:
Description: >-
Checks indentation of binary operations that span more than
one line.
Enabled: false
Style/MultilineTernaryOperator:
Description: >-
Avoid multi-line ?: (the ternary operator);
use if/unless instead.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-multiline-ternary'
Enabled: false
Style/NegatedIf:
Description: >-
Favor unless over if for negative conditions
(or control flow or).
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#unless-for-negatives'
Enabled: false
Style/NegatedWhile:
Description: 'Favor until over while for negative conditions.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#until-for-negatives'
Enabled: false
Style/NestedTernaryOperator:
Description: 'Use one expression per branch in a ternary operator.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-nested-ternary'
Enabled: false
Style/Next:
Description: 'Use `next` to skip iteration instead of a condition at the end.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-nested-conditionals'
Enabled: false
Style/NilComparison:
Description: 'Prefer x.nil? to x == nil.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#predicate-methods'
Enabled: false
Style/NonNilCheck:
Description: 'Checks for redundant nil checks.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-non-nil-checks'
Enabled: false
Style/Not:
Description: 'Use ! instead of not.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#bang-not-not'
Enabled: false
Style/NumericLiterals:
Description: >-
Add underscores to large numeric literals to improve their
readability.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#underscores-in-numerics'
Enabled: false
Style/OneLineConditional:
Description: >-
Favor the ternary operator(?:) over
if/then/else/end constructs.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#ternary-operator'
Enabled: false
Style/OpMethod:
Description: 'When defining binary operators, name the argument other.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#other-arg'
Enabled: false
Style/ParenthesesAroundCondition:
Description: >-
Don't use parentheses around the condition of an
if/unless/while.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-parens-if'
Enabled: false
Style/PercentLiteralDelimiters:
Description: 'Use `%`-literal delimiters consistently'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#percent-literal-braces'
Enabled: false
Style/PercentQLiterals:
Description: 'Checks if uses of %Q/%q match the configured preference.'
Enabled: false
Style/PerlBackrefs:
Description: 'Avoid Perl-style regex back references.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-perl-regexp-last-matchers'
Enabled: false
Style/PredicateName:
Description: 'Check the names of predicate methods.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#bool-methods-qmark'
Enabled: false
Style/Proc:
Description: 'Use proc instead of Proc.new.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#proc'
Enabled: false
Style/RaiseArgs:
Description: 'Checks the arguments passed to raise/fail.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#exception-class-messages'
Enabled: false
Style/RedundantBegin:
Description: "Don't use begin blocks when they are not needed."
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#begin-implicit'
Enabled: false
Style/RedundantException:
Description: "Checks for an obsolete RuntimeException argument in raise/fail."
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-explicit-runtimeerror'
Enabled: false
Style/RedundantReturn:
Description: "Don't use return where it's not required."
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-explicit-return'
Enabled: false
Style/RedundantSelf:
Description: "Don't use self where it's not needed."
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-self-unless-required'
Enabled: false
Style/RegexpLiteral:
Description: >-
Use %r for regular expressions matching more than
`MaxSlashes` '/' characters.
Use %r only for regular expressions matching more than
`MaxSlashes` '/' character.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#percent-r'
Enabled: false
Style/RescueModifier:
Description: 'Avoid using rescue in its modifier form.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-rescue-modifiers'
Enabled: false
Style/SelfAssignment:
Description: >-
Checks for places where self-assignment shorthand should have
been used.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#self-assignment'
Enabled: false
Style/Semicolon:
Description: "Don't use semicolons to terminate expressions."
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-semicolon'
Enabled: false
Style/SignalException:
Description: 'Checks for proper usage of fail and raise.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#fail-method'
Enabled: false
Style/SingleLineBlockParams:
Description: 'Enforces the names of some block params.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#reduce-blocks'
Enabled: false
Style/SingleLineMethods:
Description: 'Avoid single-line methods.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-single-line-methods'
Enabled: false
Style/SingleSpaceBeforeFirstArg:
Description: >-
Checks that exactly one space is used between a method name
and the first argument for method calls without parentheses.
Enabled: false
Style/SpaceAfterColon:
Description: 'Use spaces after colons.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#spaces-operators'
Enabled: false
Style/SpaceAfterComma:
Description: 'Use spaces after commas.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#spaces-operators'
Enabled: false
Style/SpaceAfterControlKeyword:
Description: 'Use spaces after if/elsif/unless/while/until/case/when.'
Enabled: false
Style/SpaceAfterMethodName:
Description: >-
Do not put a space between a method name and the opening
parenthesis in a method definition.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#parens-no-spaces'
Enabled: false
Style/SpaceAfterNot:
Description: Tracks redundant space after the ! operator.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-space-bang'
Enabled: false
Style/SpaceAfterSemicolon:
Description: 'Use spaces after semicolons.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#spaces-operators'
Enabled: false
Style/SpaceBeforeBlockBraces:
Description: >-
Checks that the left block brace has or doesn't have space
before it.
Enabled: false
Style/SpaceBeforeComma:
Description: 'No spaces before commas.'
Enabled: false
Style/SpaceBeforeComment:
Description: >-
Checks for missing space between code and a comment on the
same line.
Enabled: false
Style/SpaceBeforeSemicolon:
Description: 'No spaces before semicolons.'
Enabled: false
Style/SpaceInsideBlockBraces:
Description: >-
Checks that block braces have or don't have surrounding space.
For blocks taking parameters, checks that the left brace has
or doesn't have trailing space.
Enabled: false
Style/SpaceAroundEqualsInParameterDefault:
Description: >-
Checks that the equals signs in parameter default assignments
have or don't have surrounding space depending on
configuration.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#spaces-around-equals'
Enabled: false
Style/SpaceAroundOperators:
Description: 'Use spaces around operators.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#spaces-operators'
Enabled: false
Style/SpaceBeforeModifierKeyword:
Description: 'Put a space before the modifier keyword.'
Enabled: false
Style/SpaceInsideBrackets:
Description: 'No spaces after [ or before ].'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-spaces-braces'
Enabled: false
Style/SpaceInsideHashLiteralBraces:
Description: "Use spaces inside hash literal braces - or don't."
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#spaces-operators'
Enabled: true
Style/SpaceInsideParens:
Description: 'No spaces after ( or before ).'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-spaces-braces'
Enabled: false
Style/SpaceInsideRangeLiteral:
Description: 'No spaces inside range literals.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-space-inside-range-literals'
Enabled: false
Style/SpecialGlobalVars:
Description: 'Avoid Perl-style global variables.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-cryptic-perlisms'
Enabled: false
Style/StringLiterals:
Description: 'Checks if uses of quotes match the configured preference.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#consistent-string-literals'
Enabled: false
Style/StringLiteralsInInterpolation:
Description: >-
Checks if uses of quotes inside expressions in interpolated
strings match the configured preference.
Enabled: false
Style/SymbolProc:
Description: 'Use symbols as procs instead of blocks when possible.'
Enabled: false
Style/Tab:
Description: 'No hard tabs.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#spaces-indentation'
Enabled: false
Style/TrailingBlankLines:
Description: 'Checks trailing blank lines and final newline.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#newline-eof'
Enabled: true
Style/TrailingComma:
Description: 'Checks for trailing comma in parameter lists and literals.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-trailing-array-commas'
Enabled: false
Style/TrailingWhitespace:
Description: 'Avoid trailing whitespace.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-trailing-whitespace'
Enabled: false
Style/TrivialAccessors:
Description: 'Prefer attr_* methods to trivial readers/writers.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#attr_family'
Enabled: false
Style/UnlessElse:
Description: >-
Do not use unless with else. Rewrite these with the positive
case first.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-else-with-unless'
Enabled: false
Style/UnneededCapitalW:
Description: 'Checks for %W when interpolation is not needed.'
Enabled: false
Style/UnneededPercentQ:
Description: 'Checks for %q/%Q when single quotes or double quotes would do.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#percent-q'
Enabled: false
Style/UnneededPercentX:
Description: 'Checks for %x when `` would do.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#percent-x'
Enabled: false
Style/VariableInterpolation:
Description: >-
Don't interpolate global, instance and class variables
directly in strings.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#curlies-interpolate'
Enabled: false
Style/VariableName:
Description: 'Use the configured style when naming variables.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#snake-case-symbols-methods-vars'
Enabled: false
Style/WhenThen:
Description: 'Use when x then ... for one-line cases.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#one-line-cases'
Enabled: false
Style/WhileUntilDo:
Description: 'Checks for redundant do after while or until.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-multiline-while-do'
Enabled: false
Style/WhileUntilModifier:
Description: >-
Favor modifier while/until usage when you have a
single-line body.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#while-as-a-modifier'
Enabled: false
Style/WordArray:
Description: 'Use %w or %W for arrays of words.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#percent-w'
Enabled: false
#################### Metrics ################################
Metrics/AbcSize:
Description: >-
A calculated magnitude based on number of assignments,
branches, and conditions.
Enabled: false
Metrics/BlockNesting:
Description: 'Avoid excessive block nesting'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#three-is-the-number-thou-shalt-count'
Enabled: false
Metrics/ClassLength:
Description: 'Avoid classes longer than 100 lines of code.'
Enabled: false
Metrics/CyclomaticComplexity:
Description: >-
A complexity metric that is strongly correlated to the number
of test cases needed to validate a method.
Enabled: false
Metrics/LineLength:
Description: 'Limit lines to 80 characters.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#80-character-limits'
Enabled: false
Metrics/MethodLength:
Description: 'Avoid methods longer than 10 lines of code.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#short-methods'
Enabled: false
Metrics/ParameterLists:
Description: 'Avoid parameter lists longer than three or four parameters.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#too-many-params'
Enabled: false
Metrics/PerceivedComplexity:
Description: >-
A complexity metric geared towards measuring complexity for a
human reader.
Enabled: false
#################### Lint ################################
### Warnings
Lint/AmbiguousOperator:
Description: >-
Checks for ambiguous operators in the first argument of a
method invocation without parentheses.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#parens-as-args'
Enabled: false
Lint/AmbiguousRegexpLiteral:
Description: >-
Checks for ambiguous regexp literals in the first argument of
a method invocation without parenthesis.
Enabled: false
Lint/AssignmentInCondition:
Description: "Don't use assignment in conditions."
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#safe-assignment-in-condition'
Enabled: false
Lint/BlockAlignment:
Description: 'Align block ends correctly.'
Enabled: false
Lint/ConditionPosition:
Description: >-
Checks for condition placed in a confusing position relative to
the keyword.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#same-line-condition'
Enabled: false
Lint/Debugger:
Description: 'Check for debugger calls.'
Enabled: false
Lint/DefEndAlignment:
Description: 'Align ends corresponding to defs correctly.'
Enabled: false
Lint/DeprecatedClassMethods:
Description: 'Check for deprecated class method calls.'
Enabled: false
Lint/ElseLayout:
Description: 'Check for odd code arrangement in an else block.'
Enabled: false
Lint/EmptyEnsure:
Description: 'Checks for empty ensure block.'
Enabled: false
Lint/EmptyInterpolation:
Description: 'Checks for empty string interpolation.'
Enabled: false
Lint/EndAlignment:
Description: 'Align ends correctly.'
Enabled: false
Lint/EndInMethod:
Description: 'END blocks should not be placed inside method definitions.'
Enabled: false
Lint/EnsureReturn:
Description: 'Do not use return in an ensure block.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-return-ensure'
Enabled: false
Lint/Eval:
Description: 'The use of eval represents a serious security risk.'
Enabled: false
Lint/HandleExceptions:
Description: "Don't suppress exception."
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#dont-hide-exceptions'
Enabled: false
Lint/InvalidCharacterLiteral:
Description: >-
Checks for invalid character literals with a non-escaped
whitespace character.
Enabled: false
Lint/LiteralInCondition:
Description: 'Checks of literals used in conditions.'
Enabled: false
Lint/LiteralInInterpolation:
Description: 'Checks for literals used in interpolation.'
Enabled: false
Lint/Loop:
Description: >-
Use Kernel#loop with break rather than begin/end/until or
begin/end/while for post-loop tests.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#loop-with-break'
Enabled: false
Lint/ParenthesesAsGroupedExpression:
Description: >-
Checks for method calls with a space before the opening
parenthesis.
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#parens-no-spaces'
Enabled: false
Lint/RequireParentheses:
Description: >-
Use parentheses in the method call to avoid confusion
about precedence.
Enabled: false
Lint/RescueException:
Description: 'Avoid rescuing the Exception class.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-blind-rescues'
Enabled: false
Lint/ShadowingOuterLocalVariable:
Description: >-
Do not use the same name as outer local variable
for block arguments or block local variables.
Enabled: false
Lint/SpaceBeforeFirstArg:
Description: >-
Put a space between a method name and the first argument
in a method call without parentheses.
Enabled: false
Lint/StringConversionInInterpolation:
Description: 'Checks for Object#to_s usage in string interpolation.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#no-to-s'
Enabled: false
Lint/UnderscorePrefixedVariableName:
Description: 'Do not use prefix `_` for a variable that is used.'
Enabled: true
Lint/UnusedBlockArgument:
Description: 'Checks for unused block arguments.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#underscore-unused-vars'
Enabled: false
Lint/UnusedMethodArgument:
Description: 'Checks for unused method arguments.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#underscore-unused-vars'
Enabled: false
Lint/UnreachableCode:
Description: 'Unreachable code.'
Enabled: false
Lint/UselessAccessModifier:
Description: 'Checks for useless access modifiers.'
Enabled: false
Lint/UselessAssignment:
Description: 'Checks for useless assignment to a local variable.'
StyleGuide: 'https://github.com/bbatsov/ruby-style-guide#underscore-unused-vars'
Enabled: false
Lint/UselessComparison:
Description: 'Checks for comparison of something with itself.'
Enabled: false
Lint/UselessElseWithoutRescue:
Description: 'Checks for useless `else` in `begin..end` without `rescue`.'
Enabled: false
Lint/UselessSetterCall:
Description: 'Checks for useless setter call to a local variable.'
Enabled: false
Lint/Void:
Description: 'Possible use of operator/literal/variable in void context.'
Enabled: false
##################### Rails ##################################
Rails/ActionFilter:
Description: 'Enforces consistent use of action filter methods.'
Enabled: false
Rails/DefaultScope:
Description: 'Checks if the argument passed to default_scope is a block.'
Enabled: false
Rails/Delegate:
Description: 'Prefer delegate method for delegations.'
Enabled: false
Rails/HasAndBelongsToMany:
Description: 'Prefer has_many :through to has_and_belongs_to_many.'
Enabled: true
Rails/Output:
Description: 'Checks for calls to puts, print, etc.'
Enabled: true
Rails/ReadWriteAttribute:
Description: >-
Checks for read_attribute(:attr) and
write_attribute(:attr, val).
Enabled: false
Rails/ScopeArgs:
Description: 'Checks the arguments of ActiveRecord scopes.'
Enabled: false
Rails/Validation:
Description: 'Use validates :attribute, hash of validations.'
Enabled: false
# Exclude some of GitLab files
#
#
AllCops:
RunRailsCops: true
Exclude:
- 'spec/**/*'
- 'features/**/*'
- 'vendor/**/*'
- 'db/**/*'
- 'tmp/**/*'
- 'bin/**/*'
- 'lib/backup/**/*'
- 'lib/tasks/**/*'
- 'lib/email_validator.rb'
- 'lib/gitlab/upgrader.rb'
- 'lib/gitlab/seeder.rb'
......@@ -8,7 +8,7 @@ v 7.8.0
- Better UI for project services page
- Cleaner UI for web editor
- Add diff syntax highlighting in email-on-push service notifications (Hannes Rosenögger)
-
- Add API endpoint to fetch all changes on a MergeRequest (Jeroen van Baarsen)
-
-
- Allow more variations for commit messages closing issues (Julien Bianchi and Hannes Rosenögger)
......@@ -25,10 +25,12 @@ v 7.8.0
- Upgrade Sidekiq gem to version 3.3.0
- Stop git zombie creation during force push check
- Show success/error messages for test setting button in services
-
- Added Rubocop for code style checks
- Fix commits pagination
-
-
- Async load a branch information at the commit page
- Disable blacklist validation for project names
- Allow configuring protection of the default branch upon first push (Marco Wessel)
-
-
- Add a commit calendar to the user profile (Hannes Rosenögger)
......@@ -42,7 +44,7 @@ v 7.8.0
- Password reset token validity increased from 2 hours to 2 days since it is also send on account creation.
-
-
-
- Enable raw image paste from clipboard, currently Chrome only (Marco Cyriacks)
-
-
- Add action property to merge request hook (Julien Bianchi)
......@@ -53,15 +55,20 @@ v 7.8.0
- Add a new API function that retrieves all issues assigned to a single milestone (Justin Whear and Hannes Rosenögger)
-
-
-
-
- API: Access groups with their path (Julien Bianchi)
- Added link to milestone and keeping resource context on smaller viewports for issues and merge requests (Jason Blanchard)
-
-
- API: Add support for editing an existing project (Mika Mäenpää and Hannes Rosenögger)
-
-
-
- When test web hook - show error message instead of 500 error page if connection to hook url was reset
- Added support for firing system hooks on group create/destroy and adding/removing users to group (Boyan Tabakov)
- Added persistent collapse button for left side nav bar (Jason Blanchard)
v 7.7.2
- Update GitLab Shell to version 2.4.2 that fixes a bug when developers can push to protected branch
- Fix issue when LDAP user can't login with existing GitLab account
v 7.7.1
- Improve mention autocomplete performance
......
......@@ -208,8 +208,6 @@ group :development do
gem 'better_errors'
gem 'binding_of_caller'
gem 'rails_best_practices'
# Docs generator
gem "sdoc"
......@@ -219,11 +217,12 @@ end
group :development, :test do
gem 'coveralls', require: false
gem 'rubocop', '0.28.0', require: false
# gem 'rails-dev-tweaks'
gem 'spinach-rails'
gem "rspec-rails"
gem "capybara", '~> 2.2.1'
gem "pry"
gem "pry-rails"
gem "awesome_print"
gem "database_cleaner"
gem "launchy"
......@@ -256,7 +255,7 @@ end
group :test do
gem "simplecov", require: false
gem "shoulda-matchers", "~> 2.1.0"
gem "shoulda-matchers", "~> 2.7.0"
gem 'email_spec'
gem "webmock"
gem 'test_after_commit'
......
......@@ -37,6 +37,9 @@ GEM
rake (>= 0.8.7)
arel (5.0.1.20140414130214)
asciidoctor (0.1.4)
ast (2.0.0)
astrolabe (1.3.0)
parser (>= 2.2.0.pre.3, < 3.0)
attr_required (1.0.0)
awesome_print (1.2.0)
axiom-types (0.0.5)
......@@ -67,8 +70,6 @@ GEM
timers (~> 4.0.0)
charlock_holmes (0.6.9.4)
cliver (0.3.2)
code_analyzer (0.4.3)
sexp_processor
coderay (1.1.0)
coercible (1.0.0)
descendants_tracker (~> 0.0.1)
......@@ -354,6 +355,8 @@ GEM
org-ruby (0.9.12)
rubypants (~> 0.2)
orm_adapter (0.5.0)
parser (2.2.0.2)
ast (>= 1.1, < 3.0)
pg (0.15.1)
phantomjs (1.9.2.0)
poltergeist (1.5.1)
......@@ -363,10 +366,13 @@ GEM
websocket-driver (>= 0.2.0)
polyglot (0.3.4)
posix-spawn (0.3.9)
powerpack (0.0.9)
pry (0.9.12.4)
coderay (~> 1.0)
method_source (~> 0.8)
slop (~> 3.4)
pry-rails (0.3.2)
pry (>= 0.9.10)
pyu-ruby-sasl (0.0.3.3)
quiet_assets (1.0.2)
railties (>= 3.1, < 5.0)
......@@ -403,20 +409,12 @@ GEM
sprockets-rails (~> 2.0)
rails_autolink (1.1.6)
rails (> 3.1)
rails_best_practices (1.14.4)
activesupport
awesome_print
code_analyzer (>= 0.4.3)
colored
erubis
i18n
require_all
ruby-progressbar
railties (4.1.1)
actionpack (= 4.1.1)
activesupport (= 4.1.1)
rake (>= 0.8.7)
thor (>= 0.18.1, < 2.0)
rainbow (2.0.0)
raindrops (0.13.0)
rake (10.3.2)
raphael-rails (2.1.2)
......@@ -447,7 +445,6 @@ GEM
redis (>= 2.2)
ref (1.0.5)
request_store (1.0.5)
require_all (1.3.2)
rest-client (1.6.7)
mime-types (>= 1.16)
rinku (1.7.3)
......@@ -467,7 +464,13 @@ GEM
rspec-core (~> 2.14.0)
rspec-expectations (~> 2.14.0)
rspec-mocks (~> 2.14.0)
ruby-progressbar (1.2.0)
rubocop (0.28.0)
astrolabe (~> 1.3)
parser (>= 2.2.0.pre.7, < 3.0)
powerpack (~> 0.0.6)
rainbow (>= 1.99.1, < 3.0)
ruby-progressbar (~> 1.4)
ruby-progressbar (1.7.1)
rubyntlm (0.4.0)
rubypants (0.2.0)
rugged (0.21.2)
......@@ -495,8 +498,7 @@ GEM
semantic-ui-sass (1.8.0.0)
sass (~> 3.2)
settingslogic (2.0.9)
sexp_processor (4.4.0)
shoulda-matchers (2.1.0)
shoulda-matchers (2.7.0)
activesupport (>= 3.0.0)
sidekiq (3.3.0)
celluloid (>= 0.16.0)
......@@ -700,7 +702,7 @@ DEPENDENCIES
org-ruby (= 0.9.12)
pg
poltergeist (~> 1.5.1)
pry
pry-rails
quiet_assets (~> 1.0.1)
rack-attack
rack-cors
......@@ -708,7 +710,6 @@ DEPENDENCIES
rack-oauth2 (~> 1.0.5)
rails (~> 4.1.0)
rails_autolink (~> 1.1)
rails_best_practices
raphael-rails (~> 2.1.2)
rb-fsevent
rb-inotify
......@@ -717,6 +718,7 @@ DEPENDENCIES
redis-rails
request_store
rspec-rails
rubocop (= 0.28.0)
rugments
sanitize (~> 2.0)
sass-rails (~> 4.0.2)
......@@ -725,7 +727,7 @@ DEPENDENCIES
select2-rails
semantic-ui-sass (~> 1.8.0)
settingslogic
shoulda-matchers (~> 2.1.0)
shoulda-matchers (~> 2.7.0)
sidekiq (~> 3.3)
sidetiq (= 0.6.3)
simplecov
......
......@@ -9,8 +9,6 @@ class @calendar
cal.init
itemName: ["commit"]
data: timestamps
domain: "year"
subDomain: "month"
start: new Date(starting_year, starting_month)
domainLabelFormat: "%b"
id: "cal-heatmap"
......
......@@ -13,6 +13,8 @@ class @DropzoneInput
form_textarea = $(form).find("textarea.markdown-area")
form_textarea.wrap "<div class=\"div-dropzone\"></div>"
form_textarea.bind 'paste', (event) =>
handlePaste(event)
form_dropzone = $(form).find('.div-dropzone')
form_dropzone.parent().addClass "div-dropzone-wrapper"
......@@ -133,25 +135,18 @@ class @DropzoneInput
formatLink = (str) ->
"![" + str.alt + "](" + str.url + ")"
handlePaste = (e) ->
e.preventDefault()
my_event = e.originalEvent
if my_event.clipboardData and my_event.clipboardData.items
processItem(my_event)
processItem = (e) ->
image = isImage(e)
handlePaste = (event) ->
pasteEvent = event.originalEvent
if pasteEvent.clipboardData and pasteEvent.clipboardData.items
image = isImage(pasteEvent)
if image
filename = getFilename(e) or "image.png"
event.preventDefault()
filename = getFilename(pasteEvent) or "image.png"
text = "{{" + filename + "}}"
pasteText(text)
uploadFile image.getAsFile(), filename
else
text = e.clipboardData.getData("text/plain")
pasteText(text)
isImage = (data) ->
i = 0
while i < data.clipboardData.items.length
......
......@@ -24,3 +24,18 @@ $ ->
$(window).resize ->
responsive_resize()
return
$(document).on("click", '.toggle-nav-collapse', (e) ->
e.preventDefault()
collapsed = 'page-sidebar-collapsed'
expanded = 'page-sidebar-expanded'
if $('.page-with-sidebar').hasClass(collapsed)
$('.page-with-sidebar').removeClass(collapsed).addClass(expanded)
$('.toggle-nav-collapse i').removeClass('fa-angle-right').addClass('fa-angle-left')
$.cookie("collapsed_nav", "false", { path: '/' })
else
$('.page-with-sidebar').removeClass(expanded).addClass(collapsed)
$('.toggle-nav-collapse i').removeClass('fa-angle-left').addClass('fa-angle-right')
$.cookie("collapsed_nav", "true", { path: '/' })
)
......@@ -15,6 +15,10 @@
&.s24 { margin-right: 4px; }
}
&.avatar-tile {
@include border-radius(0px);
}
&.s16 { width: 16px; height: 16px; margin-right: 6px; }
&.s24 { width: 24px; height: 24px; margin-right: 8px; }
&.s26 { width: 26px; height: 26px; margin-right: 8px; }
......
......@@ -97,7 +97,17 @@
.dash-project-avatar {
float: left;
.avatar {
margin-top: -8px;
margin-left: -15px;
@include border-radius(0px);
}
.identicon {
line-height: 40px;
}
}
.dash-project-access-icon {
float: left;
margin-right: 5px;
......
......@@ -40,12 +40,12 @@
font-size: $code_font_size;
.old {
span.idiff {
background-color: #F99;
background-color: #f8cbcb;
}
}
.new {
span.idiff {
background-color: #8F8;
background-color: #a6f3a6;
}
}
.unfold {
......@@ -84,7 +84,7 @@
padding: 0px;
border: none;
background: #F5F5F5;
color: #666;
color: rgba(0,0,0,0.3);
padding: 0px 5px;
border-right: 1px solid #ccc;
text-align: right;
......@@ -96,7 +96,7 @@
float: left;
width: 35px;
font-weight: normal;
color: #666;
color: rgba(0,0,0,0.3);
&:hover {
text-decoration: underline;
}
......@@ -114,13 +114,13 @@
.line_holder {
&.old .old_line,
&.old .new_line {
background: #FCC;
border-color: #E7BABA;
background: #ffdddd;
border-color: #f1c0c0;
}
&.new .old_line,
&.new .new_line {
background: #CFC;
border-color: #B9ECB9;
background: #dbffdb;
border-color: #c1e9c1;
}
}
.line_content {
......@@ -129,10 +129,10 @@
padding: 0px 0.5em;
border: none;
&.new {
background: #CFD;
background: #eaffea;
}
&.old {
background: #FDD;
background: #ffecec;
}
&.matched {
color: #ccc;
......
.page-with-sidebar {
background: #F5F5F5;
......@@ -101,9 +99,7 @@
}
@mixin expanded-sidebar {
.page-with-sidebar {
padding-left: $sidebar_width;
}
.sidebar-wrapper {
width: $sidebar_width;
......@@ -122,9 +118,7 @@
}
@mixin folded-sidebar {
.page-with-sidebar {
padding-left: 50px;
}
.sidebar-wrapper {
width: 52px;
......@@ -150,10 +144,33 @@
}
}
.collapse-nav a {
position: fixed;
bottom: 15px;
padding: 10px;
background: #DDD;
}
@media (max-width: $screen-md-max) {
.page-sidebar-collapsed {
@include folded-sidebar;
}
.page-sidebar-expanded {
@include folded-sidebar;
}
.collapse-nav {
display: none;
}
}
@media(min-width: $screen-md-max) {
.page-sidebar-collapsed {
@include folded-sidebar;
}
.page-sidebar-expanded {
@include expanded-sidebar;
}
}
......@@ -81,7 +81,7 @@ ul.notes {
.diff-file .notes_holder {
font-size: 13px;
line-height: 18px;
font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
font-family: $regular_font;
td {
border: 1px solid #ddd;
......
......@@ -22,6 +22,7 @@ class Admin::ApplicationSettingsController < Admin::ApplicationController
def application_setting_params
params.require(:application_setting).permit(
:default_projects_limit,
:default_branch_protection,
:signup_enabled,
:signin_enabled,
:gravatar_enabled,
......
......@@ -23,7 +23,7 @@ class GithubImportsController < ApplicationController
end
def jobs
jobs = current_user.created_projects.where(import_type: "github").to_json(:only => [:id, :import_status])
jobs = current_user.created_projects.where(import_type: "github").to_json(only: [:id, :import_status])
render json: jobs
end
......@@ -58,7 +58,7 @@ class GithubImportsController < ApplicationController
def octo_client
Octokit.auto_paginate = true
@octo_client ||= Octokit::Client.new(:access_token => current_user.github_access_token)
@octo_client ||= Octokit::Client.new(access_token: current_user.github_access_token)
end
def github_auth
......
......@@ -15,4 +15,3 @@ class NamespacesController < ApplicationController
end
end
end
......@@ -59,8 +59,7 @@ class Projects::BlobController < Projects::ApplicationController
def preview
@content = params[:content]
diffy = Diffy::Diff.new(@blob.data, @content, diff: '-U 3',
include_diff_info: true)
diffy = Diffy::Diff.new(@blob.data, @content, diff: '-U 3', include_diff_info: true)
@diff_lines = Gitlab::Diff::Parser.new.parse(diffy.diff.scan(/.*\n/))
render layout: false
......
......@@ -11,8 +11,6 @@ class Projects::CommitController < Projects::ApplicationController
return git_not_found! unless @commit
@line_notes = @project.notes.for_commit_id(commit.id).inline
@branches = @project.repository.branch_names_contains(commit.id)
@tags = @project.repository.tag_names_contains(commit.id)
@diffs = @commit.diffs
@note = @project.build_commit_note(commit)
@notes_count = @project.notes.for_commit_id(commit.id).count
......@@ -31,6 +29,12 @@ class Projects::CommitController < Projects::ApplicationController
end
end
def branches
@branches = @project.repository.branch_names_contains(commit.id)
@tags = @project.repository.tag_names_contains(commit.id)
render layout: false
end
def commit
@commit ||= @project.repository.commit(params[:id])
end
......
......@@ -21,4 +21,3 @@ class Projects::GroupLinksController < Projects::ApplicationController
redirect_to project_group_links_path(project)
end
end
......@@ -35,4 +35,3 @@ class Projects::RawController < Projects::ApplicationController
end
end
end
......@@ -27,7 +27,7 @@ class SnippetsController < ApplicationController
@snippets = SnippetsFinder.new.execute(current_user, {
filter: :by_user,
user: @user,
scope: params[:scope]}).
scope: params[:scope] }).
page(params[:page]).per(20)
if @user == current_user
......
class UsersController < ApplicationController
skip_before_filter :authenticate_user!, only: [:show, :activities]
skip_before_filter :authenticate_user!
before_filter :set_user
layout :determine_layout
def show
@user = User.find_by_username!(params[:username])
unless current_user || @user.public_profile?
return authenticate_user!
end
# Projects user can view
visible_projects = ProjectsFinder.new.execute(current_user)
authorized_projects_ids = visible_projects.pluck(:id)
......@@ -25,19 +20,22 @@ class UsersController < ApplicationController
@title = @user.name
# Get user repositories and collect timestamps for commits
user_repositories = visible_projects.map(&:repository)
calendar = Gitlab::CommitsCalendar.new(user_repositories, @user)
@timestamps = calendar.timestamps
@starting_year = (Time.now - 1.year).strftime("%Y")
@starting_month = Date.today.strftime("%m").to_i
respond_to do |format|
format.html
format.atom { render layout: false }
end
end
def calendar
visible_projects = ProjectsFinder.new.execute(current_user)
calendar = Gitlab::CommitsCalendar.new(visible_projects, @user)
@timestamps = calendar.timestamps
@starting_year = calendar.starting_year
@starting_month = calendar.starting_month
render 'calendar', layout: false
end
def determine_layout
if current_user
'navless'
......@@ -45,4 +43,14 @@ class UsersController < ApplicationController
'public_users'
end
end
private
def set_user
@user = User.find_by_username!(params[:username])
unless current_user || @user.public_profile?
return authenticate_user!
end
end
end
......@@ -7,7 +7,8 @@ class NotesFinder
# Default to 0 to remain compatible with old clients
last_fetched_at = Time.at(params.fetch(:last_fetched_at, 0).to_i)
notes = case target_type
notes =
case target_type
when "commit"
project.notes.for_commit_id(target_id).not_inline.fresh
when "issue"
......
......@@ -75,9 +75,9 @@ module ApplicationHelper
options[:class] ||= ''
options[:class] << ' identicon'
bg_key = project.id % 7
style = "background-color: ##{ allowed_colors.values[bg_key] }; color: #555"
content_tag(:div, class: options[:class],
style: "background-color: ##{ allowed_colors.values[bg_key] }; color: #555") do
content_tag(:div, class: options[:class], style: style) do
project.name[0, 1].upcase
end
end
......@@ -247,15 +247,6 @@ module ApplicationHelper
Gitlab::MarkdownHelper.gitlab_markdown?(filename)
end
def spinner(text = nil, visible = false)
css_class = 'loading'
css_class << ' hide' unless visible
content_tag :div, class: css_class do
content_tag(:i, nil, class: 'fa fa-spinner fa-spin') + text
end
end
def link_to(name = nil, options = nil, html_options = nil, &block)
begin
uri = URI(options)
......@@ -324,4 +315,12 @@ module ApplicationHelper
profile_key_path(key)
end
end
def nav_sidebar_class
if nav_menu_collapsed?
"page-sidebar-collapsed"
else
"page-sidebar-expanded"
end
end
end
......@@ -65,8 +65,7 @@ module CommitsHelper
branches.sort.map do |branch|
link_to(project_tree_path(project, branch)) do
content_tag :span, class: 'label label-gray' do
content_tag(:i, nil, class: 'fa fa-code-fork') + ' ' +
branch
icon('code-fork') + ' ' + branch
end
end
end.join(" ").html_safe
......@@ -78,8 +77,7 @@ module CommitsHelper
sorted.map do |tag|
link_to(project_commits_path(project, project.repository.find_tag(tag).name)) do
content_tag :span, class: 'label label-gray' do
content_tag(:i, nil, class: 'fa fa-tag') + ' ' +
tag
icon('tag') + ' ' + tag
end
end
end.join(" ").html_safe
......@@ -114,7 +112,8 @@ module CommitsHelper
person_name = user.nil? ? source_name : user.name
person_email = user.nil? ? source_email : user.email
text = if options[:avatar]
text =
if options[:avatar]
avatar = image_tag(avatar_icon(person_email, options[:size]), class: "avatar #{"s#{options[:size]}" if options[:size]}", width: options[:size], alt: "")
%Q{#{avatar} <span class="commit-#{options[:source]}-name">#{person_name}</span>}
else
......
......@@ -10,6 +10,6 @@ module CompareHelper
end
def compare_mr_path
new_project_merge_request_path(@project, merge_request: {source_branch: params[:to], target_branch: params[:from]})
new_project_merge_request_path(@project, merge_request: { source_branch: params[:to], target_branch: params[:from] })
end
end
......@@ -31,7 +31,7 @@ module EmailsHelper
end
def add_email_highlight_css
Rugments::Themes::Github.render(:scope => '.highlight')
Rugments::Themes::Github.render(scope: '.highlight')
end
def color_email_diff(diffcontent)
......
......@@ -27,18 +27,17 @@ module EventsHelper
content_tag :li, class: "filter_icon #{active}" do
link_to request.path, class: 'has_tooltip event_filter_link', id: "#{key}_event_filter", 'data-original-title' => tooltip do
content_tag(:i, nil, class: icon_for_event[key]) +
content_tag(:span, ' ' + tooltip)
icon(icon_for_event[key]) + content_tag(:span, ' ' + tooltip)
end
end
end
def icon_for_event
{
EventFilter.push => 'fa fa-upload',
EventFilter.merged => 'fa fa-check-square-o',
EventFilter.comments => 'fa fa-comments',
EventFilter.team => 'fa fa-user',
EventFilter.push => 'upload',
EventFilter.merged => 'check-square-o',
EventFilter.comments => 'comments',
EventFilter.team => 'user',
}
end
......
module IconsHelper
# Creates an icon tag given icon name(s) and possible icon modifiers.
#
# Right now this method simply delegates directly to `fa_icon` from the
# font-awesome-rails gem, but should we ever use a different icon pack in the
# future we won't have to change hundreds of method calls.
def icon(names, options = {})
fa_icon(names, options)
end
def spinner(text = nil, visible = false)
css_class = 'loading'
css_class << ' hide' unless visible
content_tag :div, class: css_class do
icon('spinner spin') + text
end
end
def boolean_to_icon(value)
if value.to_s == "true"
content_tag :i, nil, class: 'fa fa-circle cgreen'
icon('circle', class: 'cgreen')
else
content_tag :i, nil, class: 'fa fa-power-off clgray'
icon('power-off', class: 'clgray')
end
end
def public_icon
content_tag :i, nil, class: 'fa fa-globe'
icon('globe')
end
def internal_icon
content_tag :i, nil, class: 'fa fa-shield'
icon('shield')
end
def private_icon
content_tag :i, nil, class: 'fa fa-lock'
icon('lock')
end
end
......@@ -49,7 +49,7 @@ module IssuesHelper
ts << capture_haml do
haml_tag :span do
haml_concat '&middot;'
haml_concat '<i class="fa fa-edit" title="edited"></i> '
haml_concat icon('edit', title: 'edited')
haml_concat time_ago_with_tooltip(issue.updated_at, 'bottom', 'issue_edited_ago')
end
end
......
......@@ -15,12 +15,14 @@ module MergeRequestsHelper
end
def new_mr_from_push_event(event, target_project)
return :merge_request => {
return {
merge_request: {
source_project_id: event.project.id,
target_project_id: target_project.id,
source_branch: event.branch_name,
target_branch: target_project.repository.root_ref
}
}
end
def mr_css_classes(mr)
......
module NavHelper
def nav_menu_collapsed?
cookies[:collapsed_nav] == 'true'
end
end
......@@ -22,7 +22,7 @@ module NotesHelper
ts << capture_haml do
haml_tag :span do
haml_concat '&middot;'
haml_concat '<i class="fa fa-edit" title="edited"></i> '
haml_concat icon('edit', title: 'edited')
haml_concat time_ago_with_tooltip(note.updated_at, 'bottom', 'note_edited_ago')
end
end
......@@ -57,7 +57,7 @@ module NotesHelper
button_tag(class: 'btn add-diff-note js-add-diff-note-button',
data: data,
title: 'Add a comment to this line') do
content_tag :i, nil, class: 'fa fa-comment-o'
icon('comment-o')
end
end
......@@ -74,7 +74,7 @@ module NotesHelper
button_tag class: 'btn reply-btn js-discussion-reply-button',
data: data, title: 'Add a reply' do
link_text = content_tag(:i, nil, class: 'fa fa-comment')
link_text = icon('comment')
link_text << ' Reply'
end
end
......
module NotificationsHelper
def notification_icon(notification)
if notification.disabled?
content_tag :i, nil, class: 'fa fa-volume-off ns-mute'
icon('volume-off', class: 'ns-mute')
elsif notification.participating?
content_tag :i, nil, class: 'fa fa-volume-down ns-part'
icon('volume-down', class: 'ns-part')
elsif notification.watch?
content_tag :i, nil, class: 'fa fa-volume-up ns-watch'
icon('volume-up', class: 'ns-watch')
else
content_tag :i, nil, class: 'fa fa-circle-o ns-default'
icon('circle-o', class: 'ns-default')
end
end
end
......@@ -83,7 +83,7 @@ module ProjectsHelper
' Star'
end
content_tag('i', ' ', class: 'fa fa-star') + toggle_text
icon('star') + toggle_text
end
count_html = content_tag('span', class: 'count') do
......@@ -95,7 +95,7 @@ module ProjectsHelper
class: cls,
method: :post,
remote: true,
data: {type: 'json'}
data: { type: 'json' }
}
......@@ -107,7 +107,7 @@ module ProjectsHelper
end
def link_to_toggle_fork
out = content_tag(:i, '', class: 'fa fa-code-fork')
out = icon('code-fork')
out << ' Fork'
out << content_tag(:span, class: 'count') do
@project.forks_count.to_s
......@@ -262,4 +262,3 @@ module ProjectsHelper
end
end
end
......@@ -38,13 +38,8 @@ module TreeHelper
#
# type - String type of the tree item; either 'folder' or 'file'
def tree_icon(type)
icon_class = if type == 'folder'
'fa fa-folder'
else
'fa fa-file-o'
end
content_tag :i, nil, class: icon_class
icon_class = type == 'folder' ? 'folder' : 'file-o'
icon(icon_class)
end
def tree_hex_class(content)
......
......@@ -2,9 +2,12 @@ class Appearance < ActiveRecord::Base
validates :title, presence: true
validates :description, presence: true
validates :logo, file_size: { maximum: 1000.kilobytes.to_i }
validates :dark_logo, file_size: { maximum: 1000.kilobytes.to_i },
validates :dark_logo,
file_size: { maximum: 1000.kilobytes.to_i },
presence: true, if: :light_logo?
validates :light_logo, file_size: { maximum: 1000.kilobytes.to_i },
validates :light_logo,
file_size: { maximum: 1000.kilobytes.to_i },
presence: true, if: :dark_logo?
mount_uploader :logo, AttachmentUploader
......
......@@ -4,6 +4,7 @@
#
# id :integer not null, primary key
# default_projects_limit :integer
# default_branch_protection :integer
# signup_enabled :boolean
# signin_enabled :boolean
# gravatar_enabled :boolean
......@@ -14,7 +15,8 @@
#
class ApplicationSetting < ActiveRecord::Base
validates :home_page_url, allow_blank: true,
validates :home_page_url,
allow_blank: true,
format: { with: URI::regexp(%w(http https)), message: "should be a valid url" },
if: :home_page_url_column_exist
......@@ -25,6 +27,7 @@ class ApplicationSetting < ActiveRecord::Base
def self.create_from_defaults
create(
default_projects_limit: Settings.gitlab['default_projects_limit'],
default_branch_protection: Settings.gitlab['default_branch_protection'],
signup_enabled: Settings.gitlab['signup_enabled'],
signin_enabled: Settings.gitlab['signin_enabled'],
gravatar_enabled: Settings.gravatar['enabled'],
......
......@@ -88,7 +88,8 @@ class Commit
# cut off, ellipses (`&hellp;`) are prepended to the commit message.
def description
title_end = safe_message.index("\n")
@description ||= if (!title_end && safe_message.length > 100) || (title_end && title_end > 100)
@description ||=
if (!title_end && safe_message.length > 100) || (title_end && title_end > 100)
"&hellip;".html_safe << safe_message[80..-1]
else
safe_message.split("\n", 2)[1].try(:chomp)
......
......@@ -111,7 +111,7 @@ class Group < Namespace
class << self
def search(query)
where("LOWER(namespaces.name) LIKE :query", query: "%#{query.downcase}%")
where("LOWER(namespaces.name) LIKE :query or LOWER(namespaces.path) LIKE :query", query: "%#{query.downcase}%")
end
def sort(method)
......
......@@ -44,11 +44,11 @@ class WebHook < ActiveRecord::Base
}
WebHook.post(post_url,
body: data.to_json,
headers: {"Content-Type" => "application/json"},
headers: { "Content-Type" => "application/json" },
verify: false,
basic_auth: auth)
end
rescue SocketError, Errno::ECONNREFUSED, Net::OpenTimeout => e
rescue SocketError, Errno::ECONNRESET, Errno::ECONNREFUSED, Net::OpenTimeout => e
logger.error("WebHook Error => #{e}")
false
end
......
......@@ -11,5 +11,5 @@
class Identity < ActiveRecord::Base
belongs_to :user
validates :extern_uid, allow_blank: true, uniqueness: {scope: :provider}
validates :extern_uid, allow_blank: true, uniqueness: { scope: :provider }
end
......@@ -79,7 +79,7 @@ class MergeRequest < ActiveRecord::Base
merge_request.save
end
after_transition :locked => (any - :locked) do |merge_request, transition|
after_transition locked: (any - :locked) do |merge_request, transition|
merge_request.locked_at = nil
merge_request.save
end
......
......@@ -20,12 +20,17 @@ class Namespace < ActiveRecord::Base
belongs_to :owner, class_name: "User"
validates :owner, presence: true, unless: ->(n) { n.type == "Group" }
validates :name, presence: true, uniqueness: true,
validates :name,
presence: true, uniqueness: true,
length: { within: 0..255 },
format: { with: Gitlab::Regex.name_regex,
message: Gitlab::Regex.name_regex_message }
validates :description, length: { within: 0..255 }
validates :path, uniqueness: { case_sensitive: false }, presence: true, length: { within: 1..255 },
validates :path,
uniqueness: { case_sensitive: false },
presence: true,
length: { within: 1..255 },
exclusion: { in: Gitlab::Blacklist.path },
format: { with: Gitlab::Regex.path_regex,
message: Gitlab::Regex.path_regex_message }
......
......@@ -14,7 +14,7 @@
# merge_requests_enabled :boolean default(TRUE), not null
# wiki_enabled :boolean default(TRUE), not null
# namespace_id :integer
# issues_tracker :string(255) default('gitlab'), not null
# issues_tracker :string(255) default("gitlab"), not null
# issues_tracker_id :string(255)
# snippets_enabled :boolean default(TRUE), not null
# last_activity_at :datetime
......@@ -115,11 +115,14 @@ class Project < ActiveRecord::Base
# Validations
validates :creator, presence: true, on: :create
validates :description, length: { maximum: 2000 }, allow_blank: true
validates :name, presence: true, length: { within: 0..255 },
validates :name,
presence: true,
length: { within: 0..255 },
format: { with: Gitlab::Regex.project_name_regex,
message: Gitlab::Regex.project_regex_message }
validates :path, presence: true, length: { within: 0..255 },
exclusion: { in: Gitlab::Blacklist.path },
validates :path,
presence: true,
length: { within: 0..255 },
format: { with: Gitlab::Regex.path_regex,
message: Gitlab::Regex.path_regex_message }
validates :issues_enabled, :merge_requests_enabled,
......@@ -163,22 +166,22 @@ class Project < ActiveRecord::Base
end
event :import_finish do
transition :started => :finished
transition started: :finished
end
event :import_fail do
transition :started => :failed
transition started: :failed
end
event :import_retry do
transition :failed => :started
transition failed: :started
end
state :started
state :finished
state :failed
after_transition any => :started, :do => :add_import_job
after_transition any => :started, do: :add_import_job
end
class << self
......
class ProjectContributions
attr_reader :project, :user
def initialize(project, user)
@project, @user = project, user
end
def commits_log
repository = project.repository
if !repository.exists? || repository.empty?
return {}
end
Rails.cache.fetch(cache_key) do
repository.commits_per_day_for_user(user)
end
end
def cache_key
"#{Date.today.to_s}-commits-log-#{project.id}-#{user.email}"
end
end
......@@ -17,13 +17,19 @@ class BambooService < CiService
prop_accessor :bamboo_url, :build_key, :username, :password
validates :bamboo_url, presence: true,
format: { with: URI::regexp }, if: :activated?
validates :bamboo_url,
presence: true,
format: { with: URI::regexp },
if: :activated?
validates :build_key, presence: true, if: :activated?
validates :username, presence: true,
if: ->(service) { service.password? }, if: :activated?
validates :password, presence: true,
if: ->(service) { service.username? }, if: :activated?
validates :username,
presence: true,
if: ->(service) { service.password? },
if: :activated?
validates :password,
presence: true,
if: ->(service) { service.username? },
if: :activated?
attr_accessor :response
......
# == Schema Information
#
# Table name: services
#
# id :integer not null, primary key
# type :string(255)
# title :string(255)
# project_id :integer not null
# created_at :datetime
# updated_at :datetime
# active :boolean default(FALSE), not null
# properties :text
#
class CustomIssueTrackerService < IssueTrackerService
prop_accessor :title, :description, :project_url, :issues_url, :new_issue_url
......@@ -27,8 +41,8 @@ class CustomIssueTrackerService < IssueTrackerService
{ type: 'text', name: 'title', placeholder: title },
{ type: 'text', name: 'description', placeholder: description },
{ type: 'text', name: 'project_url', placeholder: 'Project url' },
{ type: 'text', name: 'issues_url', placeholder: 'Issue url'},
{ type: 'text', name: 'new_issue_url', placeholder: 'New Issue url'}
{ type: 'text', name: 'issues_url', placeholder: 'Issue url' },
{ type: 'text', name: 'new_issue_url', placeholder: 'New Issue url' }
]
end
......
......@@ -81,7 +81,7 @@ class GitlabCiService < CiService
def fields
[
{ type: 'text', name: 'token', placeholder: 'GitLab CI project specific token' },
{ type: 'text', name: 'project_url', placeholder: 'http://ci.gitlabhq.com/projects/3'}
{ type: 'text', name: 'project_url', placeholder: 'http://ci.gitlabhq.com/projects/3' }
]
end
end
# == Schema Information
#
# Table name: services
#
# id :integer not null, primary key
# type :string(255)
# title :string(255)
# project_id :integer not null
# created_at :datetime
# updated_at :datetime
# active :boolean default(FALSE), not null
# properties :text
#
class GitlabIssueTrackerService < IssueTrackerService
include Rails.application.routes.url_helpers
prop_accessor :title, :description, :project_url, :issues_url, :new_issue_url
......
# == Schema Information
#
# Table name: services
#
# id :integer not null, primary key
# type :string(255)
# title :string(255)
# project_id :integer not null
# created_at :datetime
# updated_at :datetime
# active :boolean default(FALSE), not null
# properties :text
#
class IssueTrackerService < Service
validates :project_url, :issues_url, :new_issue_url, presence: true, if: :activated?
......@@ -30,8 +44,8 @@ class IssueTrackerService < Service
[
{ type: 'text', name: 'description', placeholder: description },
{ type: 'text', name: 'project_url', placeholder: 'Project url' },
{ type: 'text', name: 'issues_url', placeholder: 'Issue url'},
{ type: 'text', name: 'new_issue_url', placeholder: 'New Issue url'}
{ type: 'text', name: 'issues_url', placeholder: 'Issue url' },
{ type: 'text', name: 'new_issue_url', placeholder: 'New Issue url' }
]
end
......
# == Schema Information
#
# Table name: services
#
# id :integer not null, primary key
# type :string(255)
# title :string(255)
# project_id :integer not null
# created_at :datetime
# updated_at :datetime
# active :boolean default(FALSE), not null
# properties :text
#
class JiraService < IssueTrackerService
include HTTParty
......
# == Schema Information
#
# Table name: services
#
# id :integer not null, primary key
# type :string(255)
# title :string(255)
# project_id :integer not null
# created_at :datetime
# updated_at :datetime
# active :boolean default(FALSE), not null
# properties :text
#
class RedmineService < IssueTrackerService
prop_accessor :title, :description, :project_url, :issues_url, :new_issue_url
......
......@@ -17,12 +17,15 @@ class TeamcityService < CiService
prop_accessor :teamcity_url, :build_type, :username, :password
validates :teamcity_url, presence: true,
validates :teamcity_url,
presence: true,
format: { with: URI::regexp }, if: :activated?
validates :build_type, presence: true, if: :activated?
validates :username, presence: true,
validates :username,
presence: true,
if: ->(service) { service.password? }, if: :activated?
validates :password, presence: true,
validates :password,
presence: true,
if: ->(service) { service.username? }, if: :activated?
attr_accessor :response
......
......@@ -136,7 +136,7 @@ class ProjectWiki
def commit_details(action, message = nil, title = nil)
commit_message = message || default_message(action, title)
{email: @user.email, name: @user.name, message: commit_message}
{ email: @user.email, name: @user.name, message: commit_message }
end
def default_message(action, title)
......
......@@ -30,7 +30,7 @@ class Repository
commit = Gitlab::Git::Commit.find(raw_repository, id)
commit = Commit.new(commit) if commit
commit
rescue Rugged::OdbError => ex
rescue Rugged::OdbError
nil
end
......@@ -61,25 +61,25 @@ class Repository
end
def add_branch(branch_name, ref)
Rails.cache.delete(cache_key(:branch_names))
cache.expire(:branch_names)
gitlab_shell.add_branch(path_with_namespace, branch_name, ref)
end
def add_tag(tag_name, ref, message = nil)
Rails.cache.delete(cache_key(:tag_names))
cache.expire(:tag_names)
gitlab_shell.add_tag(path_with_namespace, tag_name, ref, message)
end
def rm_branch(branch_name)
Rails.cache.delete(cache_key(:branch_names))
cache.expire(:branch_names)
gitlab_shell.rm_branch(path_with_namespace, branch_name)
end
def rm_tag(tag_name)
Rails.cache.delete(cache_key(:tag_names))
cache.expire(:tag_names)
gitlab_shell.rm_tag(path_with_namespace, tag_name)
end
......@@ -97,19 +97,15 @@ class Repository
end
def branch_names
Rails.cache.fetch(cache_key(:branch_names)) do
raw_repository.branch_names
end
cache.fetch(:branch_names) { raw_repository.branch_names }
end
def tag_names
Rails.cache.fetch(cache_key(:tag_names)) do
raw_repository.tag_names
end
cache.fetch(:tag_names) { raw_repository.tag_names }
end
def commit_count
Rails.cache.fetch(cache_key(:commit_count)) do
cache.fetch(:commit_count) do
begin
raw_repository.commit_count(self.root_ref)
rescue
......@@ -121,26 +117,19 @@ class Repository
# Return repo size in megabytes
# Cached in redis
def size
Rails.cache.fetch(cache_key(:size)) do
raw_repository.size
end
cache.fetch(:size) { raw_repository.size }
end
def expire_cache
Rails.cache.delete(cache_key(:size))
Rails.cache.delete(cache_key(:branch_names))
Rails.cache.delete(cache_key(:tag_names))
Rails.cache.delete(cache_key(:commit_count))
Rails.cache.delete(cache_key(:graph_log))
Rails.cache.delete(cache_key(:readme))
Rails.cache.delete(cache_key(:version))
Rails.cache.delete(cache_key(:contribution_guide))
%i(size branch_names tag_names commit_count graph_log
readme version contribution_guide).each do |key|
cache.expire(key)
end
end
def graph_log
Rails.cache.fetch(cache_key(:graph_log)) do
commits = raw_repository.log(limit: 6000,
skip_merges: true,
cache.fetch(:graph_log) do
commits = raw_repository.log(limit: 6000, skip_merges: true,
ref: root_ref)
commits.map do |rugged_commit|
......@@ -176,10 +165,6 @@ class Repository
end
end
def cache_key(type)
"#{type}:#{path_with_namespace}"
end
def method_missing(m, *args, &block)
raw_repository.send(m, *args, &block)
end
......@@ -199,13 +184,11 @@ class Repository
end
def readme
Rails.cache.fetch(cache_key(:readme)) do
tree(:head).readme
end
cache.fetch(:readme) { tree(:head).readme }
end
def version
Rails.cache.fetch(cache_key(:version)) do
cache.fetch(:version) do
tree(:head).blobs.find do |file|
file.name.downcase == 'version'
end
......@@ -213,9 +196,7 @@ class Repository
end
def contribution_guide
Rails.cache.fetch(cache_key(:contribution_guide)) do
tree(:head).contribution_guide
end
cache.fetch(:contribution_guide) { tree(:head).contribution_guide }
end
def head_commit
......@@ -351,4 +332,10 @@ class Repository
[]
end
end
private
def cache
@cache ||= RepositoryCache.new(path_with_namespace)
end
end
......@@ -29,7 +29,9 @@ class Snippet < ActiveRecord::Base
validates :author, presence: true
validates :title, presence: true, length: { within: 0..255 }
validates :file_name, presence: true, length: { within: 0..255 },
validates :file_name,
presence: true,
length: { within: 0..255 },
format: { with: Gitlab::Regex.path_regex,
message: Gitlab::Regex.path_regex_message }
validates :content, presence: true
......
......@@ -113,10 +113,12 @@ class User < ActiveRecord::Base
# Validations
#
validates :name, presence: true
validates :email, presence: true, email: {strict_mode: true}, uniqueness: true
validates :email, presence: true, email: { strict_mode: true }, uniqueness: true
validates :bio, length: { maximum: 255 }, allow_blank: true
validates :projects_limit, presence: true, numericality: {greater_than_or_equal_to: 0}
validates :username, presence: true, uniqueness: { case_sensitive: false },
validates :projects_limit, presence: true, numericality: { greater_than_or_equal_to: 0 }
validates :username,
presence: true,
uniqueness: { case_sensitive: false },
exclusion: { in: Gitlab::Blacklist.path },
format: { with: Gitlab::Regex.username_regex,
message: Gitlab::Regex.username_regex_message }
......
......@@ -43,7 +43,7 @@ class WikiPage
@attributes[:slug]
end
alias :to_param :slug
alias_method :to_param, :slug
# The formatted title of this page.
def title
......
class GitPushService
attr_accessor :project, :user, :push_data, :push_commits
include Gitlab::CurrentSettings
include Gitlab::Access
# This method will be called after each git update
# and only if the provided user and project is present in GitLab.
......@@ -29,8 +31,12 @@ class GitPushService
if is_default_branch?(ref)
# Initial push to the default branch. Take the full history of that branch as "newly pushed".
@push_commits = project.repository.commits(newrev)
# Default branch is protected by default
project.protected_branches.create({ name: project.default_branch })
# Set protection on the default branch if configured
if (current_application_settings.default_branch_protection != PROTECTION_NONE)
developers_can_push = current_application_settings.default_branch_protection == PROTECTION_DEV_CAN_PUSH ? true : false
project.protected_branches.create({ name: project.default_branch, developers_can_push: developers_can_push })
end
else
# Use the pushed commits that aren't reachable by the default branch
# as a heuristic. This may include more commits than are actually pushed, but
......
......@@ -5,7 +5,8 @@ module Projects
end
def execute(note_type, note_id)
participating = if note_type && note_id
participating =
if note_type && note_id
participants_in(note_type, note_id)
else
[]
......
......@@ -25,6 +25,10 @@
= f.label :default_projects_limit, class: 'control-label'
.col-sm-10
= f.number_field :default_projects_limit, class: 'form-control'
.form-group
= f.label :default_branch_protection, class: 'control-label'
.col-sm-10
= f.select :default_branch_protection, options_for_select(Gitlab::Access.protection_options, @application_setting.default_branch_protection), {}, class: 'form-control'
.form-group
= f.label :home_page_url, class: 'control-label'
.col-sm-10
......
......@@ -91,7 +91,7 @@
%div.prepend-top-10
= select_tag :access_level, options_for_select(GroupMember.access_level_roles), class: "project-access-select select2"
%hr
= button_tag 'Add users into group', class: "btn btn-create"
= button_tag 'Add users to group', class: "btn btn-create"
.panel.panel-default
.panel-heading
%h3.panel-title
......
......@@ -10,7 +10,8 @@
- groups.each do |group|
%li.group-row
= link_to group_path(id: group.path), class: dom_class(group) do
= image_tag group_icon(group.path), class: "avatar s24"
.dash-project-avatar
= image_tag group_icon(group.path), class: "avatar s40"
%span.group-name.filter-title
= truncate(group.name, length: 35)
%span.arrow
......
= link_to project_path(project), class: dom_class(project) do
.dash-project-avatar
= project_icon(project.to_param, alt: '', class: 'avatar s40')
.dash-project-access-icon
= visibility_level_icon(project.visibility_level)
.dash-project-avatar
= project_icon(project.to_param, alt: '', class: 'avatar s24')
%span.str-truncated
%span.namespace-name
- if project.namespace
......
......@@ -12,4 +12,4 @@
%strong= link_to "here", help_page_path("permissions", "permissions"), class: "vlink"
.form-actions
= f.submit 'Add users into group', class: "btn btn-create"
= f.submit 'Add users to group', class: "btn btn-create"
......@@ -12,10 +12,10 @@
- projects.each do |project|
%li.project-row
= link_to project_path(project), class: dom_class(project) do
.dash-project-avatar
= project_icon(project.to_param, alt: '', class: 'avatar s40')
.dash-project-access-icon
= visibility_level_icon(project.visibility_level)
.dash-project-avatar
= project_icon(project.to_param, alt: '', class: 'avatar s24')
%span.str-truncated
%span.project-name
= project.name
......
.dashboard
%div
= image_tag group_icon(@group.path), class: "avatar s90"
= image_tag group_icon(@group.path), class: "avatar avatar-tile s90"
.clearfix
%h2
= @group.name
......
- if nav_menu_collapsed?
= link_to icon('angle-right'), '#', class: 'toggle-nav-collapse'
- else
= link_to icon('angle-left'), '#', class: 'toggle-nav-collapse'
- if defined?(sidebar)
.page-with-sidebar
.page-with-sidebar{ class: nav_sidebar_class }
= render "layouts/broadcast"
.sidebar-wrapper
= render(sidebar)
.collapse-nav
= render partial: 'layouts/collapse_button'
.content-wrapper
.container-fluid
.content
......
......@@ -30,5 +30,5 @@
%code
:erb
<% lines.each do |line| %>
<%= highlight(@blob.name, line, true).html_safe %>
<%= highlight(@blob.name, line.force_encoding("utf-8"), true).html_safe %>
<% end %>
......@@ -37,23 +37,8 @@
- @commit.parents.each do |parent|
= link_to parent.short_id, project_commit_path(@project, parent)
.commit-info-row
- if @branches.any?
%span
- branch = commit_default_branch(@project, @branches)
= link_to(project_tree_path(@project, branch)) do
%span.label.label-gray
%i.fa.fa-code-fork
= branch
- if @branches.any? || @tags.any?
= link_to("#", class: "js-details-expand") do
%span.label.label-gray
\...
%span.js-details-content.hide
- if @branches.any?
= commit_branches_links(@project, @branches)
- if @tags.any?
= commit_tags_links(@project, @tags)
.commit-info-row.branches
%i.fa.fa-spinner.fa-spin
.commit-box
%h3.commit-title
......@@ -61,3 +46,7 @@
- if @commit.description.present?
%pre.commit-description
= preserve(gfm(escape_once(@commit.description)))
:coffeescript
$ ->
$(".commit-info-row.branches").load("#{branches_project_commit_path(@project, @commit.id)}")
\ No newline at end of file
- if @branches.any?
%span
- branch = commit_default_branch(@project, @branches)
= link_to(project_tree_path(@project, branch)) do
%span.label.label-gray
%i.fa.fa-code-fork
= branch
- if @branches.any? || @tags.any?
= link_to("#", class: "js-details-expand") do
%span.label.label-gray
\...
%span.js-details-content.hide
- if @branches.any?
= commit_branches_links(@project, @branches)
- if @tags.any?
= commit_tags_links(@project, @tags)
\ No newline at end of file
......@@ -3,8 +3,7 @@
.project-edit-content
%div
%h3.page-title
Project settings:
%p.light Some settings, such as "Transfer Project", are hidden inside the danger area below.
Project settings
%hr
.panel-body
= form_for @project, remote: true, html: { multipart: true, class: "edit_project form-horizontal" }, authenticity_token: true do |f|
......
......@@ -10,7 +10,7 @@
You can
= link_to project_new_blob_path(@project, 'master'), class: 'btn btn-new btn-lg' do
add a file
&nbsp;or push it via command line.
&nbsp;or do a push via the command line.
%h4
%strong Command line instructions
......
......@@ -13,7 +13,7 @@
= link_to_member(@project, participant, name: false, size: 24)
.voting_notes#notes= render "projects/notes/notes_with_form"
.col-md-3.hidden-sm.hidden-xs
.col-md-3
%div
.clearfix
%span.slead.has_tooltip{:"data-original-title" => 'Cross-project reference'}
......
......@@ -2,23 +2,21 @@
%div.prepend-top-20
%p
Assignee:
- if can?(current_user, :modify_issue, @issue)
= project_users_select_tag('issue[assignee_id]', placeholder: 'Select assignee', class: 'custom-form-control js-select2 js-assignee', selected: @issue.assignee_id)
- elsif issue.assignee
- if issue.assignee
= link_to_member(@project, @issue.assignee)
- else
None
none
- if can?(current_user, :modify_issue, @issue)
= project_users_select_tag('issue[assignee_id]', placeholder: 'Select assignee', class: 'custom-form-control js-select2 js-assignee', selected: @issue.assignee_id)
%div.prepend-top-20
%p
Milestone:
- if issue.milestone
#{link_to @issue.milestone.title, project_milestone_path(@project, @issue.milestone)}
- else
none
- if can?(current_user, :modify_issue, @issue)
= f.select(:milestone_id, milestone_options(@issue), { include_blank: "Select milestone" }, {class: 'select2 select2-compact js-select2 js-milestone'})
= hidden_field_tag :issue_context
= f.submit class: 'btn'
- elsif issue.milestone
= link_to project_milestone_path(@project, @issue.milestone) do
= @issue.milestone.title
- else
None
......@@ -3,8 +3,15 @@
:plain
$("##{dom_id(@issue)}").fadeOut();
- elsif params[:issue_context]
$('.context').html("#{escape_javascript(render partial: 'issue_context', locals: { issue: @issue })}");
$('.context').effect('highlight');
- if @issue.milestone
$('.milestone-nav-link').replaceWith("<span class='milestone-nav-link'>| <span class='light'>Milestone</span> #{escape_javascript(link_to @issue.milestone.title, project_milestone_path(@issue.project, @issue.milestone))}</span>")
- else
$('.milestone-nav-link').html('')
$('select.select2').select2({width: 'resolve', dropdownAutoWidth: true})
$('.edit-issue.inline-update input[type="submit"]').hide();
new ProjectUsersSelect();
new Issue();
......@@ -9,7 +9,7 @@
.col-md-9
= render "projects/merge_requests/show/participants"
= render "projects/notes/notes_with_form"
.col-md-3.hidden-sm.hidden-xs
.col-md-3
.clearfix
%span.slead.has_tooltip{:"data-original-title" => 'Cross-project reference'}
= cross_project_reference(@project, @merge_request)
......@@ -18,7 +18,7 @@
%cite.cgray
= render partial: 'projects/merge_requests/show/context', locals: { merge_request: @merge_request }
%hr
.votes-holder.hidden-sm.hidden-xs
.votes-holder
%h6 Votes
#votes= render 'votes/votes_block', votable: @merge_request
......
......@@ -2,22 +2,22 @@
%div.prepend-top-20
%p
Assignee:
- if can?(current_user, :modify_merge_request, @merge_request)
= project_users_select_tag('merge_request[assignee_id]', placeholder: 'Select assignee', class: 'custom-form-control js-select2 js-assignee', selected: @merge_request.assignee_id)
- elsif merge_request.assignee
- if @merge_request.assignee
= link_to_member(@project, @merge_request.assignee)
- else
None
none
- if can?(current_user, :modify_merge_request, @merge_request)
= project_users_select_tag('merge_request[assignee_id]', placeholder: 'Select assignee', class: 'custom-form-control js-select2 js-assignee', selected: @merge_request.assignee_id)
%div.prepend-top-20
%p
Milestone:
- if @merge_request.milestone
%span.back-to-milestone
#{link_to @merge_request.milestone.title, project_milestone_path(@project, @merge_request.milestone)}
- else
none
- if can?(current_user, :modify_merge_request, @merge_request)
= f.select(:milestone_id, milestone_options(@merge_request), { include_blank: "Select milestone" }, {class: 'select2 select2-compact js-select2 js-milestone'})
= hidden_field_tag :merge_request_context
= f.submit class: 'btn'
- elsif merge_request.milestone
= link_to merge_request.milestone.title, project_milestone_path
- else
None
- if params[:merge_request_context]
$('.context').html("#{escape_javascript(render partial: 'projects/merge_requests/show/context', locals: { issue: @issue })}");
$('.context').effect('highlight');
new ProjectUsersSelect();
$('select.select2').select2({width: 'resolve', dropdownAutoWidth: true});
merge_request = new MergeRequest();
......@@ -19,8 +19,10 @@
%td.new_line= "..."
%td.line_content.matched= line.text
- else
%td.old_line= raw(line.type == "new" ? "&nbsp;" : line.old_pos)
%td.new_line= raw(line.type == "old" ? "&nbsp;" : line.new_pos)
%td.old_line{class: line.type == "new" ? "new" : "old"}
= raw(line.type == "new" ? "&nbsp;" : line.old_pos)
%td.new_line{class: line.type == "new" ? "new" : "old"}
= raw(line.type == "old" ? "&nbsp;" : line.new_pos)
%td.line_content{class: "noteable_line #{line.type} #{line_code}", "line_code" => line_code}= raw diff_line_content(line.text)
- if line_code == note.line_code
......
.clearfix
- groups.each do |group|
= link_to group, class: 'profile-groups-avatars', title: group.name do
= image_tag group_icon(group.path), class: 'avatar avatar-inline s40'
= link_to group, class: 'profile-groups-avatars inline', title: group.name do
= image_tag group_icon(group.path), class: 'avatar avatar-tile s40'
%h4 Calendar
#cal-heatmap.calendar
:javascript
new calendar(
......
.row
.col-md-8
%h3.page-title
= image_tag avatar_icon(@user.email, 90), class: "avatar s90", alt: ''
= image_tag avatar_icon(@user.email, 90), class: "avatar avatar-tile s90", alt: ''
= @user.name
- if @user == current_user
.pull-right
......@@ -15,15 +15,16 @@
.clearfix
- if @groups.any?
%h4 Groups:
%h4 Groups
= render 'groups', groups: @groups
%hr
%h4 Calendar:
%div= render 'calendar'
.user-calendar
%h4.center.light
%i.fa.fa-spinner.fa-spin
%hr
%h4
User Activity:
User Activity
- if current_user
%span.rss-icon.pull-right
......@@ -36,3 +37,8 @@
= render 'profile', user: @user
- if @projects.present?
= render 'projects', projects: @projects
:coffeescript
$ ->
$(".user-calendar").load("#{user_calendar_path}")
......@@ -70,7 +70,10 @@ module Gitlab
config.middleware.use Rack::Cors do
allow do
origins '*'
resource '/api/*', headers: :any, methods: [:get, :post, :options, :put, :delete]
resource '/api/*',
headers: :any,
methods: [:get, :post, :options, :put, :delete],
expose: ['Link']
end
end
......
......@@ -12,10 +12,14 @@ class Settings < Settingslogic
def build_gitlab_shell_ssh_path_prefix
if gitlab_shell.ssh_port != 22
"ssh://#{gitlab_shell.ssh_user}@#{gitlab_shell.ssh_host}:#{gitlab_shell.ssh_port}/"
else
if gitlab_shell.ssh_host.include? ':'
"[#{gitlab_shell.ssh_user}@#{gitlab_shell.ssh_host}]:"
else
"#{gitlab_shell.ssh_user}@#{gitlab_shell.ssh_host}:"
end
end
end
def build_gitlab_url
custom_port = gitlab_on_standard_port? ? nil : ":#{gitlab.port}"
......@@ -94,6 +98,7 @@ Settings['issues_tracker'] ||= {}
#
Settings['gitlab'] ||= Settingslogic.new({})
Settings.gitlab['default_projects_limit'] ||= 10
Settings.gitlab['default_branch_protection'] ||= 2
Settings.gitlab['default_can_create_group'] = true if Settings.gitlab['default_can_create_group'].nil?
Settings.gitlab['default_theme'] = Gitlab::Theme::MARS if Settings.gitlab['default_theme'].nil?
Settings.gitlab['host'] ||= 'localhost'
......@@ -155,7 +160,7 @@ Settings.gitlab_shell['ssh_path_prefix'] ||= Settings.send(:build_gitlab_shell_s
Settings['backup'] ||= Settingslogic.new({})
Settings.backup['keep_time'] ||= 0
Settings.backup['path'] = File.expand_path(Settings.backup['path'] || "tmp/backups/", Rails.root)
Settings.backup['upload'] ||= Settingslogic.new({'remote_directory' => nil, 'connection' => nil})
Settings.backup['upload'] ||= Settingslogic.new({ 'remote_directory' => nil, 'connection' => nil })
# Convert upload connection settings to use symbol keys, to make Fog happy
if Settings.backup['upload']['connection']
Settings.backup['upload']['connection'] = Hash[Settings.backup['upload']['connection'].map { |k, v| [k.to_sym, v] }]
......
......@@ -42,7 +42,8 @@ module ActsAsTaggableOn::Taggable
elsif options.delete(:any)
# get tags, drop out if nothing returned (we need at least one)
tags = if options.delete(:wild)
tags =
if options.delete(:wild)
ActsAsTaggableOn::Tag.named_like_any(tag_list)
else
ActsAsTaggableOn::Tag.named_any(tag_list)
......
......@@ -12,22 +12,30 @@ if File.exists?(aws_file)
aws_secret_access_key: AWS_CONFIG['secret_access_key'], # required
region: AWS_CONFIG['region'], # optional, defaults to 'us-east-1'
}
config.fog_directory = AWS_CONFIG['bucket'] # required
config.fog_public = false # optional, defaults to true
config.fog_attributes = {'Cache-Control'=>'max-age=315576000'} # optional, defaults to {}
config.fog_authenticated_url_expiration = 1 << 29 # optional time (in seconds) that authenticated urls will be valid.
# required
config.fog_directory = AWS_CONFIG['bucket']
# optional, defaults to true
config.fog_public = false
# optional, defaults to {}
config.fog_attributes = { 'Cache-Control'=>'max-age=315576000' }
# optional time (in seconds) that authenticated urls will be valid.
# when fog_public is false and provider is AWS or Google, defaults to 600
config.fog_authenticated_url_expiration = 1 << 29
end
# Mocking Fog requests, based on: https://github.com/carrierwaveuploader/carrierwave/wiki/How-to%3A-Test-Fog-based-uploaders
if Rails.env.test?
Fog.mock!
connection = ::Fog::Storage.new(
:aws_access_key_id => AWS_CONFIG['access_key_id'],
:aws_secret_access_key => AWS_CONFIG['secret_access_key'],
:provider => 'AWS',
:region => AWS_CONFIG['region']
aws_access_key_id: AWS_CONFIG['access_key_id'],
aws_secret_access_key: AWS_CONFIG['secret_access_key'],
provider: 'AWS',
region: AWS_CONFIG['region']
)
connection.directories.create(:key => AWS_CONFIG['bucket'])
connection.directories.create(key: AWS_CONFIG['bucket'])
end
end
......@@ -43,10 +43,10 @@ Doorkeeper.configure do
force_ssl_in_redirect_uri false
# Provide support for an owner to be assigned to each registered application (disabled by default)
# Optional parameter :confirmation => true (default false) if you want to enforce ownership of
# Optional parameter confirmation: true (default false) if you want to enforce ownership of
# a registered application
# Note: you must also run the rails g doorkeeper:application_owner generator to provide the necessary support
enable_application_owner :confirmation => false
enable_application_owner confirmation: false
# Define access token scopes for your provider
# For more information go to
......
......@@ -3,9 +3,9 @@ require 'api/api'
Gitlab::Application.routes.draw do
use_doorkeeper do
controllers :applications => 'oauth/applications',
:authorized_applications => 'oauth/authorized_applications',
:authorizations => 'oauth/authorizations'
controllers applications: 'oauth/applications',
authorized_applications: 'oauth/authorized_applications',
authorizations: 'oauth/authorizations'
end
#
# Search
......@@ -167,10 +167,9 @@ Gitlab::Application.routes.draw do
end
end
# route for commits used by the cal-heatmap
get 'u/:username/activities' => 'users#activities', as: :user_activities,
constraints: { username: /(?:[^.]|\.(?!atom$))+/, format: /atom/ },
via: :get
get 'u/:username/calendar' => 'users#calendar', as: :user_calendar,
constraints: { username: /(?:[^.]|\.(?!atom$))+/, format: /atom/ }
get '/u/:username' => 'users#show', as: :user,
constraints: { username: /(?:[^.]|\.(?!atom$))+/, format: /atom/ }
......@@ -188,7 +187,7 @@ Gitlab::Application.routes.draw do
#
# Groups Area
#
resources :groups, constraints: {id: /(?:[^.]|\.(?!atom$))+/, format: /atom/} do
resources :groups, constraints: { id: /(?:[^.]|\.(?!atom$))+/, format: /atom/ } do
member do
get :issues
get :merge_requests
......@@ -239,40 +238,44 @@ Gitlab::Application.routes.draw do
scope module: :projects do
# Blob routes:
get '/new/:id', to: 'blob#new', constraints: {id: /.+/}, as: 'new_blob'
post '/create/:id', to: 'blob#create', constraints: {id: /.+/}, as: 'create_blob'
get '/edit/:id', to: 'blob#edit', constraints: {id: /.+/}, as: 'edit_blob'
put '/update/:id', to: 'blob#update', constraints: {id: /.+/}, as: 'update_blob'
post '/preview/:id', to: 'blob#preview', constraints: {id: /.+/}, as: 'preview_blob'
get '/new/:id', to: 'blob#new', constraints: { id: /.+/ }, as: 'new_blob'
post '/create/:id', to: 'blob#create', constraints: { id: /.+/ }, as: 'create_blob'
get '/edit/:id', to: 'blob#edit', constraints: { id: /.+/ }, as: 'edit_blob'
put '/update/:id', to: 'blob#update', constraints: { id: /.+/ }, as: 'update_blob'
post '/preview/:id', to: 'blob#preview', constraints: { id: /.+/ }, as: 'preview_blob'
resources :blob, only: [:show, :destroy], constraints: { id: /.+/, format: false } do
get :diff, on: :member
end
resources :raw, only: [:show], constraints: {id: /.+/}
resources :tree, only: [:show], constraints: {id: /.+/, format: /(html|js)/ }
resources :raw, only: [:show], constraints: { id: /.+/ }
resources :tree, only: [:show], constraints: { id: /.+/, format: /(html|js)/ }
resource :avatar, only: [:show, :destroy]
resources :commit, only: [:show], constraints: {id: /[[:alnum:]]{6,40}/}
resources :commits, only: [:show], constraints: {id: /(?:[^.]|\.(?!atom$))+/, format: /atom/}
resources :commit, only: [:show], constraints: { id: /[[:alnum:]]{6,40}/ } do
get :branches, on: :member
end
resources :commits, only: [:show], constraints: { id: /(?:[^.]|\.(?!atom$))+/, format: /atom/ }
resources :compare, only: [:index, :create]
resources :blame, only: [:show], constraints: {id: /.+/}
resources :network, only: [:show], constraints: {id: /(?:[^.]|\.(?!json$))+/, format: /json/}
resources :graphs, only: [:show], constraints: {id: /(?:[^.]|\.(?!json$))+/, format: /json/} do
resources :blame, only: [:show], constraints: { id: /.+/ }
resources :network, only: [:show], constraints: { id: /(?:[^.]|\.(?!json$))+/, format: /json/ }
resources :graphs, only: [:show], constraints: { id: /(?:[^.]|\.(?!json$))+/, format: /json/ } do
member do
get :commits
end
end
get '/compare/:from...:to' => 'compare#show', :as => 'compare',
:constraints => {from: /.+/, to: /.+/}
:constraints => { from: /.+/, to: /.+/ }
resources :snippets, constraints: {id: /\d+/} do
resources :snippets, constraints: { id: /\d+/ } do
member do
get 'raw'
end
end
resources :wikis, only: [:show, :edit, :destroy, :create], constraints: {id: /[a-zA-Z.0-9_\-\/]+/} do
resources :wikis, only: [:show, :edit, :destroy, :create], constraints: { id: /[a-zA-Z.0-9_\-\/]+/ } do
collection do
get :pages
put ':id' => 'wikis#update'
......@@ -299,7 +302,7 @@ Gitlab::Application.routes.draw do
end
end
resources :deploy_keys, constraints: {id: /\d+/} do
resources :deploy_keys, constraints: { id: /\d+/ } do
member do
put :enable
put :disable
......@@ -318,16 +321,14 @@ Gitlab::Application.routes.draw do
member do
# tree viewer logs
get 'logs_tree', constraints: { id: Gitlab::Regex.git_reference_regex }
get 'logs_tree/:path' => 'refs#logs_tree',
as: :logs_file,
constraints: {
get 'logs_tree/:path' => 'refs#logs_tree', as: :logs_file, constraints: {
id: Gitlab::Regex.git_reference_regex,
path: /.*/
}
end
end
resources :merge_requests, constraints: {id: /\d+/}, except: [:destroy] do
resources :merge_requests, constraints: { id: /\d+/ }, except: [:destroy] do
member do
get :diffs
post :automerge
......@@ -342,29 +343,28 @@ Gitlab::Application.routes.draw do
end
end
resources :git_hooks, constraints: {id: /\d+/}
resources :hooks, only: [:index, :create, :destroy], constraints: {id: /\d+/} do
resources :git_hooks, constraints: { id: /\d+/ }
resources :hooks, only: [:index, :create, :destroy], constraints: { id: /\d+/ } do
member do
get :test
end
end
resources :team, controller: 'team_members', only: [:index]
resources :milestones, except: [:destroy], constraints: {id: /\d+/} do
resources :milestones, except: [:destroy], constraints: { id: /\d+/ } do
member do
put :sort_issues
put :sort_merge_requests
end
end
resources :labels, constraints: {id: /\d+/} do
resources :labels, constraints: { id: /\d+/ } do
collection do
post :generate
end
end
resources :issues, constraints: {id: /\d+/}, except: [:destroy] do
resources :issues, constraints: { id: /\d+/ }, except: [:destroy] do
collection do
post :bulk_update
end
......@@ -381,9 +381,9 @@ Gitlab::Application.routes.draw do
end
end
resources :group_links, only: [:index, :create, :destroy], constraints: {id: /\d+/}
resources :group_links, only: [:index, :create, :destroy], constraints: { id: /\d+/ }
resources :notes, only: [:index, :create, :destroy, :update], constraints: {id: /\d+/} do
resources :notes, only: [:index, :create, :destroy, :update], constraints: { id: /\d+/ } do
member do
delete :delete_attachment
end
......@@ -394,7 +394,7 @@ Gitlab::Application.routes.draw do
get "/audit_events" => "audit_events#project_log"
end
get ':id' => 'namespaces#show', constraints: {id: /(?:[^.]|\.(?!atom$))+/, format: /atom/}
get ':id' => 'namespaces#show', constraints: { id: /(?:[^.]|\.(?!atom$))+/, format: /atom/ }
root to: 'dashboard#show'
end
class AddDefaultBranchProtectionSetting < ActiveRecord::Migration
def change
add_column :application_settings, :default_branch_protection, :integer, :default => 2
end
end
......@@ -11,7 +11,7 @@
#
# It's strongly recommended that you check this file into your version control system.
ActiveRecord::Schema.define(version: 20150116234545) do
ActiveRecord::Schema.define(version: 20150125163100) do
# These are extensions that must be enabled in order to support this database
enable_extension "plpgsql"
......@@ -27,6 +27,18 @@ ActiveRecord::Schema.define(version: 20150116234545) do
t.string "light_logo"
end
create_table "application_settings", force: true do |t|
t.integer "default_projects_limit"
t.boolean "signup_enabled"
t.boolean "signin_enabled"
t.boolean "gravatar_enabled"
t.text "sign_in_text"
t.datetime "created_at"
t.datetime "updated_at"
t.string "home_page_url"
t.integer "default_branch_protection", default: 2
end
create_table "audit_events", force: true do |t|
t.integer "author_id", null: false
t.string "type", null: false
......@@ -41,17 +53,6 @@ ActiveRecord::Schema.define(version: 20150116234545) do
add_index "audit_events", ["entity_id", "entity_type"], name: "index_audit_events_on_entity_id_and_entity_type", using: :btree
add_index "audit_events", ["type"], name: "index_audit_events_on_type", using: :btree
create_table "application_settings", force: true do |t|
t.integer "default_projects_limit"
t.boolean "signup_enabled"
t.boolean "signin_enabled"
t.boolean "gravatar_enabled"
t.text "sign_in_text"
t.datetime "created_at"
t.datetime "updated_at"
t.string "home_page_url"
end
create_table "broadcast_messages", force: true do |t|
t.text "message", null: false
t.datetime "starts_at"
......@@ -378,14 +379,14 @@ ActiveRecord::Schema.define(version: 20150116234545) do
t.string "import_url"
t.integer "visibility_level", default: 0, null: false
t.boolean "archived", default: false, null: false
t.string "avatar"
t.string "import_status"
t.string "import_type"
t.string "import_source"
t.float "repository_size", default: 0.0
t.integer "star_count", default: 0, null: false
t.text "merge_requests_template"
t.integer "star_count", default: 0, null: false
t.boolean "merge_requests_rebase_enabled", default: false
t.string "avatar"
t.string "import_type"
t.string "import_source"
end
add_index "projects", ["creator_id"], name: "index_projects_on_creator_id", using: :btree
......@@ -483,6 +484,7 @@ ActiveRecord::Schema.define(version: 20150116234545) do
t.integer "notification_level", default: 1, null: false
t.datetime "password_expires_at"
t.integer "created_by_id"
t.datetime "last_credential_check_at"
t.string "avatar"
t.string "confirmation_token"
t.datetime "confirmed_at"
......@@ -490,9 +492,8 @@ ActiveRecord::Schema.define(version: 20150116234545) do
t.string "unconfirmed_email"
t.boolean "hide_no_ssh_key", default: false
t.string "website_url", default: "", null: false
t.datetime "last_credential_check_at"
t.string "github_access_token"
t.datetime "admin_email_unsubscribed_at"
t.string "github_access_token"
t.string "gitlab_access_token"
end
......
......@@ -97,7 +97,7 @@ Return values:
## Sudo
All API requests support performing an api call as if you were another user, if your private token is for an administration account. You need to pass `sudo` parameter by url or header with an id or username of the user you want to perform the operation as. If passed as header, the header name must be "SUDO" (capitals).
All API requests support performing an api call as if you were another user, if your private token is for an administration account. You need to pass `sudo` parameter by URL or header with an id or username of the user you want to perform the operation as. If passed as header, the header name must be "SUDO" (capitals).
If a non administrative `private_token` is provided then an error message will be returned with status code 403:
......@@ -142,7 +142,7 @@ When listing resources you can pass the following parameters:
- `page` (default: `1`) - page number
- `per_page` (default: `20`, max: `100`) - number of items to list per page
[Link headers](http://www.w3.org/wiki/LinkHeader) are send back with each response. These have `rel` prev/next/first/last and contain the relevant URL. Please use these instead of generating your own urls.
[Link headers](http://www.w3.org/wiki/LinkHeader) are send back with each response. These have `rel` prev/next/first/last and contain the relevant URL. Please use these instead of generating your own URLs.
## id vs iid
......
......@@ -20,7 +20,7 @@ GET /groups
]
```
You can search for groups by name or path with: `/groups?search=Rails`
You can search for groups by name or path, see below.
## Details of a group
......@@ -32,7 +32,7 @@ GET /groups/:id
Parameters:
- `id` (required) - The ID of a group
- `id` (required) - The ID or path of a group
## New group
......@@ -58,7 +58,7 @@ POST /groups/:id/projects/:project_id
Parameters:
- `id` (required) - The ID of a group
- `id` (required) - The ID or path of a group
- `project_id` (required) - The ID of a project
## Remove group
......@@ -71,7 +71,27 @@ DELETE /groups/:id
Parameters:
- `id` (required) - The ID of a user group
- `id` (required) - The ID or path of a user group
## Search for group
Get all groups that match your string in their name or path.
```
GET /groups?search=foobar
```
```json
[
{
"id": 1,
"name": "Foobar Group",
"path": "foo-bar",
"owner_id": 18,
"description": "An interesting group"
}
]
```
## Group members
......@@ -128,7 +148,7 @@ POST /groups/:id/members
Parameters:
- `id` (required) - The ID of a group
- `id` (required) - The ID or path of a group
- `user_id` (required) - The ID of a user to add
- `access_level` (required) - Project access level
......@@ -142,5 +162,5 @@ DELETE /groups/:id/members/:user_id
Parameters:
- `id` (required) - The ID of a user group
- `id` (required) - The ID or path of a user group
- `user_id` (required) - The ID of a group member
......@@ -56,7 +56,7 @@ Parameters:
"title": "v1.0",
"description": "",
"due_date": "2012-07-20",
"state": "reopenend",
"state": "reopened",
"updated_at": "2012-07-04T13:42:48Z",
"created_at": "2012-07-04T13:42:48Z"
},
......
......@@ -94,6 +94,76 @@ Parameters:
}
```
## Get single MR changes
Shows information about the merge request including its files and changes
```
GET /projects/:id/merge_request/:merge_request_id/changes
```
Parameters:
- `id` (required) - The ID of a project
- `merge_request_id` (required) - The ID of MR
```json
{
"id": 21,
"iid": 1,
"project_id": 4,
"title": "Blanditiis beatae suscipit hic assumenda et molestias nisi asperiores repellat et.",
"description": "Qui voluptatibus placeat ipsa alias quasi. Deleniti rem ut sint. Optio velit qui distinctio.",
"state": "reopened",
"created_at": "2015-02-02T19:49:39.159Z",
"updated_at": "2015-02-02T20:08:49.959Z",
"target_branch": "secret_token",
"source_branch": "version-1-9",
"upvotes": 0,
"downvotes": 0,
"author": {
"name": "Chad Hamill",
"username": "jarrett",
"id": 5,
"state": "active",
"avatar_url": "http://www.gravatar.com/avatar/b95567800f828948baf5f4160ebb2473?s=40&d=identicon"
},
"assignee": {
"name": "Administrator",
"username": "root",
"id": 1,
"state": "active",
"avatar_url": "http://www.gravatar.com/avatar/e64c7d89f26bd1972efa854d13d7dd61?s=40&d=identicon"
},
"source_project_id": 4,
"target_project_id": 4,
"labels": [ ],
"milestone": {
"id": 5,
"iid": 1,
"project_id": 4,
"title": "v2.0",
"description": "Assumenda aut placeat expedita exercitationem labore sunt enim earum.",
"state": "closed",
"created_at": "2015-02-02T19:49:26.013Z",
"updated_at": "2015-02-02T19:49:26.013Z",
"due_date": null
},
"files": [
{
"old_path": "VERSION",
"new_path": "VERSION",
"a_mode": "100644",
"b_mode": "100644",
"diff": "--- a/VERSION\ +++ b/VERSION\ @@ -1 +1 @@\ -1.9.7\ +1.9.8",
"new_file": false,
"renamed_file": false,
"deleted_file": false
}
]
}
```
## Create MR
Creates a new merge request.
......
......@@ -4,7 +4,7 @@ OAuth2 is a protocol that enables us to get access to private details of user's
Before using the OAuth2 you should create an application in user's account. Each application getting unique App ID and App Secret parameters. You should not share them.
This functianolity is based on [doorkeeper gem](https://github.com/doorkeeper-gem/doorkeeper)
This functionality is based on [doorkeeper gem](https://github.com/doorkeeper-gem/doorkeeper)
## Web Application Flow
......@@ -15,7 +15,7 @@ This flow consists from 3 steps.
### 1. Registering the client
Creat an application in user's account profile.
Create an application in user's account profile.
### 2. Requesting authorization
......
......@@ -541,7 +541,7 @@ Parameters:
}
],
"tree": "c68537c6534a02cc2b176ca1549f4ffa190b58ee",
"message": "give caolan credit where it's due (up top)",
"message": "give Caolan credit where it's due (up top)",
"author": {
"name": "Jeremy Ashkenas",
"email": "jashkenas@example.com"
......
......@@ -13,7 +13,7 @@ PUT /projects/:id/services/gitlab-ci
Parameters:
- `token` (required) - CI project token
- `project_url` (required) - CI project url
- `project_url` (required) - CI project URL
### Delete GitLab CI service
......@@ -23,23 +23,23 @@ Delete GitLab CI service settings for a project.
DELETE /projects/:id/services/gitlab-ci
```
## Hipchat
## HipChat
### Edit Hipchat service
### Edit HipChat service
Set Hipchat service for project.
Set HipChat service for project.
```
PUT /projects/:id/services/hipchat
```
Parameters:
- `token` (required) - Hipchat token
- `room` (required) - Hipchat room name
- `token` (required) - HipChat token
- `room` (required) - HipChat room name
### Delete Hipchat service
### Delete HipChat service
Delete Hipchat service for a project.
Delete HipChat service for a project.
```
DELETE /projects/:id/services/hipchat
......
......@@ -16,7 +16,7 @@ the configuration options as follows:
```yml
gravatar:
enabled: true
# gravatar urls: possible placeholders: %{hash} %{size} %{email}
# gravatar URLs: possible placeholders: %{hash} %{size} %{email}
plain_url: "http://cdn.libravatar.org/avatar/%{hash}?s=%{size}&d=identicon"
```
......@@ -25,14 +25,14 @@ the configuration options as follows:
```yml
gravatar:
enabled: true
# gravatar urls: possible placeholders: %{hash} %{size} %{email}
# gravatar URLs: possible placeholders: %{hash} %{size} %{email}
ssl_url: "https://seccdn.libravatar.org/avatar/%{hash}?s=%{size}&d=identicon"
```
## Self-hosted
If you are [running your own libravatar service](http://wiki.libravatar.org/running_your_own/) the url will be different in the configuration
but the important part is to provide the same placeholders so GitLab can parse the url correctly.
If you are [running your own libravatar service](http://wiki.libravatar.org/running_your_own/) the URL will be different in the configuration
but the important part is to provide the same placeholders so GitLab can parse the URL correctly.
For example, you host a service on `http://libravatar.example.com` the `plain_url` you need to supply in `gitlab.yml` is
......@@ -65,5 +65,5 @@ Run `sudo gitlab-ctl reconfigure` for changes to take effect.
[Libravatar supports different sets](http://wiki.libravatar.org/api/) of `missing images` for emails not found on the Libravatar service.
In order to use a different set other than `identicon`, replace `&d=identicon` portion of the url with another supported set.
For example, you can use `retro` set in which case url would look like: `plain_url: "http://cdn.libravatar.org/avatar/%{hash}?s=%{size}&d=retro"`
In order to use a different set other than `identicon`, replace `&d=identicon` portion of the URL with another supported set.
For example, you can use `retro` set in which case the URL would look like: `plain_url: "http://cdn.libravatar.org/avatar/%{hash}?s=%{size}&d=retro"`
......@@ -16,8 +16,8 @@ You can imagine GitLab as a physical office.
They can be stored in a warehouse.
This can be either a hard disk, or something more complex, such as a NFS filesystem;
**NginX** acts like the front-desk.
Users come to NginX and request actions to be done by workers in the office;
**Nginx** acts like the front-desk.
Users come to Nginx and request actions to be done by workers in the office;
**The database** is a series of metal file cabinets with information on:
- The goods in the warehouse (metadata, issues, merge requests etc);
......@@ -70,7 +70,7 @@ To summarize here's the [directory structure of the `git` user home directory](.
ps aux | grep '^git'
GitLab has several components to operate. As a system user (i.e. any user that is not the `git` user) it requires a persistent database (MySQL/PostreSQL) and redis database. It also uses Apache httpd or nginx to proxypass Unicorn. As the `git` user it starts Sidekiq and Unicorn (a simple ruby HTTP server running on port `8080` by default). Under the GitLab user there are normally 4 processes: `unicorn_rails master` (1 process), `unicorn_rails worker` (2 processes), `sidekiq` (1 process).
GitLab has several components to operate. As a system user (i.e. any user that is not the `git` user) it requires a persistent database (MySQL/PostreSQL) and redis database. It also uses Apache httpd or Nginx to proxypass Unicorn. As the `git` user it starts Sidekiq and Unicorn (a simple ruby HTTP server running on port `8080` by default). Under the GitLab user there are normally 4 processes: `unicorn_rails master` (1 process), `unicorn_rails worker` (2 processes), `sidekiq` (1 process).
### Repository access
......@@ -146,13 +146,13 @@ nginx
Apache httpd
- [Explanation of apache logs](http://httpd.apache.org/docs/2.2/logs.html).
- [Explanation of Apache logs](http://httpd.apache.org/docs/2.2/logs.html).
- `/var/log/apache2/` contains error and output logs (on Ubuntu).
- `/var/log/httpd/` contains error and output logs (on RHEL).
redis
- `/var/log/redis/redis.log` there are also logrotated logs there.
- `/var/log/redis/redis.log` there are also log-rotated logs there.
PostgreSQL
......
......@@ -26,7 +26,7 @@ We use [these build scripts](https://gitlab.com/gitlab-org/gitlab-ci/blob/master
# Build configuration on [Semaphore](https://semaphoreapp.com/gitlabhq/gitlabhq/) for testing the [GitHub.com repo](https://github.com/gitlabhq/gitlabhq)
- Language: Ruby
- Ruby verion: 2.1.2
- Ruby version: 2.1.2
- database.yml: pg
Build commands
......
......@@ -280,7 +280,7 @@ We recommend using a PostgreSQL database. For MySQL check [MySQL setup guide](da
GitLab Shell is an SSH access and repository management software developed specially for GitLab.
# Run the installation task for gitlab-shell (replace `REDIS_URL` if needed):
sudo -u git -H bundle exec rake gitlab:shell:install[v2.4.1] REDIS_URL=unix:/var/run/redis/redis.sock RAILS_ENV=production
sudo -u git -H bundle exec rake gitlab:shell:install[v2.4.2] REDIS_URL=unix:/var/run/redis/redis.sock RAILS_ENV=production
# By default, the gitlab-shell config is generated from your main GitLab config.
# You can review (and modify) the gitlab-shell config as follows:
......
......@@ -7,7 +7,7 @@
- Ubuntu
- Debian
- CentOS
- RedHat Enterprise Linux (please use the CentOS packages and instructions)
- Red Hat Enterprise Linux (please use the CentOS packages and instructions)
- Scientific Linux (please use the CentOS packages and instructions)
- Oracle Linux (please use the CentOS packages and instructions)
......
......@@ -14,7 +14,7 @@ See the documentation below for details on how to configure these services.
## Project services
Integration with services such as Campfire, Flowdock, Gemnasium, HipChat, PivotalTracker and Slack are available in the from of a Project Service.
Integration with services such as Campfire, Flowdock, Gemnasium, HipChat, Pivotal Tracker, and Slack are available in the form of a Project Service.
You can find these within GitLab in the Services page under Project Settings if you are at least a master on the project.
Project Services are a bit like plugins in that they allow a lot of freedom in adding functionality to GitLab, for example there is also a service that can send an email every time someone pushes new commits.
Because GitLab is open source we can ship with the code and tests for all plugins.
......
......@@ -6,6 +6,6 @@ GitLab has a great issue tracker but you can also use an external issue tracker
- clicking 'New issue' on the project dashboard creates a new JIRA issue;
- To reference JIRA issue PROJECT-1234 in comments, use syntax PROJECT-1234. Commit messages get turned into HTML links to the corresponding JIRA issue.
![jira screenshot](jira-integration-points.png)
![Jira screenshot](jira-integration-points.png)
You can configure the integration in the gitlab.yml configuration file.
# GitLab buttons in gmail
# GitLab buttons in Gmail
GitLab supports [Google actions in email](https://developers.google.com/gmail/markup/actions/actions-overview).
......@@ -25,4 +25,4 @@ If you receive "No errors detected" message from the tester you can send the ema
```bash
bundle exec rake gitlab:mail_google_schema_whitelisting RAILS_ENV=production SEND=true
``
```
......@@ -2,7 +2,7 @@
This documentation is for enabling shibboleth with gitlab-omnibus package.
In order to enable Shibboleth support in gitlab we need to use Apache instead of Nginx (It may be possible to use Nginx, however I did not found way to easily configure nginx that is bundled in gitlab-omnibus package). Apache uses mod_shib2 module for shibboleth authentication and can pass attributes as headers to omniauth-shibboleth provider.
In order to enable Shibboleth support in gitlab we need to use Apache instead of Nginx (It may be possible to use Nginx, however I did not found way to easily configure Nginx that is bundled in gitlab-omnibus package). Apache uses mod_shib2 module for shibboleth authentication and can pass attributes as headers to omniauth-shibboleth provider.
To enable the Shibboleth OmniAuth provider you must:
......@@ -10,11 +10,11 @@ To enable the Shibboleth OmniAuth provider you must:
1. Configure Apache shibboleth module. Installation and configuration of module it self is out of scope of this document.
Check https://wiki.shibboleth.net/ for more info.
1. You can find Apache config in gitlab-reciepes (https://github.com/gitlabhq/gitlab-recipes/blob/master/web-server/apache/gitlab-ssl.conf)
1. You can find Apache config in gitlab-recipes (https://github.com/gitlabhq/gitlab-recipes/blob/master/web-server/apache/gitlab-ssl.conf)
Following changes are needed to enable shibboleth:
protect omniauth-shibboleth callback url:
protect omniauth-shibboleth callback URL:
```
<Location /users/auth/shibboleth/callback>
AuthType shibboleth
......@@ -32,9 +32,9 @@ protect omniauth-shibboleth callback url:
SetHandler shib
</Location>
```
exclude shibboleth urls from rewriting, add "RewriteCond %{REQUEST_URI} !/Shibboleth.sso" and "RewriteCond %{REQUEST_URI} !/shibboleth-sp", config should look like this:
exclude shibboleth URLs from rewriting, add "RewriteCond %{REQUEST_URI} !/Shibboleth.sso" and "RewriteCond %{REQUEST_URI} !/shibboleth-sp", config should look like this:
```
#apache equivalent of nginx try files
# Apache equivalent of Nginx try files
RewriteEngine on
RewriteCond %{DOCUMENT_ROOT}/%{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_URI} !/Shibboleth.sso
......@@ -50,7 +50,7 @@ File it should look like this:
external_url 'https://gitlab.example.com'
gitlab_rails['internal_api_url'] = 'https://gitlab.example.com'
# disable nginx
# disable Nginx
nginx['enable'] = false
gitlab_rails['omniauth_allow_single_sign_on'] = true
......
......@@ -35,7 +35,7 @@ After Slack is ready we need to setup GitLab. Here are the steps to achieve this
1. Fill in your Slack details
- Mark it as active
- Paste in the webhook url you got from Slack
- Paste in the webhook URL you got from Slack
Have fun :)
......
......@@ -6,7 +6,7 @@
* [Newlines](#newlines)
* [Multiple underscores in words](#multiple-underscores-in-words)
* [URL autolinking](#url-autolinking)
* [URL auto-linking](#url-autolinking)
* [Code and Syntax Highlighting](#code-and-syntax-highlighting)
* [Emoji](#emoji)
* [Special GitLab references](#special-gitlab-references)
......@@ -40,7 +40,7 @@ You can use GFM in
- milestones
- wiki pages
You can also use other rich text files in GitLab. You might have to install a depency to do so. Please see the [github-markup gem readme](https://github.com/gitlabhq/markup#markups) for more information.
You can also use other rich text files in GitLab. You might have to install a dependency to do so. Please see the [github-markup gem readme](https://github.com/gitlabhq/markup#markups) for more information.
## Newlines
......@@ -68,7 +68,7 @@ It is not reasonable to italicize just _part_ of a word, especially when you're
perform_complicated_task
do_this_and_do_that_and_another_thing
## URL autolinking
## URL auto-linking
GFM will autolink standard URLs you copy and paste into your text. So if you want to link to a URL (instead of a textural link), you can simply put the URL in verbatim and it will be turned into a link to that URL.
......@@ -250,17 +250,17 @@ The IDs are generated from the content of the header according to the following
For example:
```
###### ..Ab_c-d. e [anchor](url) ![alt text](url)..
###### ..Ab_c-d. e [anchor](URL) ![alt text](URL)..
```
which renders as:
###### ..Ab_c-d. e [anchor](url) ![alt text](url)..
###### ..Ab_c-d. e [anchor](URL) ![alt text](URL)..
will first be converted by step 1) into a string like:
```
..Ab_c-d. e &lt;a href="url">anchor&lt;/a> &lt;img src="url" alt="alt text"/>..
..Ab_c-d. e &lt;a href="URL">anchor&lt;/a> &lt;img src="URL" alt="alt text"/>..
```
After removing the tags in step 2) we get:
......@@ -277,8 +277,8 @@ ab_c-d-e-anchor
Note in particular how:
- for markdown anchors `[text](url)`, only the `text` is used
- markdown images `![alt](url)` are completely ignored
- for markdown anchors `[text](URL)`, only the `text` is used
- markdown images `![alt](URL)` are completely ignored
## Emphasis
......
......@@ -4,16 +4,16 @@ __Project integrations with external services for continuous integration and mor
## Services
- Assemblia
- [Atlassian Bamboo CI](bamboo.md) An Atlassian product for continous integration.
- Assembla
- [Atlassian Bamboo CI](bamboo.md) An Atlassian product for continuous integration.
- Build box
- Campfire
- Emails on push
- Flowdock
- Gemnasium
- GitLab CI
- Hipchat
- PivotalTracker
- HipChat
- Pivotal Tracker
- Pushover
- Slack
- TeamCity
......@@ -13,7 +13,7 @@ You can only restore a backup to exactly the same version of GitLab that you cre
# use this command if you've installed GitLab with the Omnibus package
sudo gitlab-rake gitlab:backup:create
# if you've installed GitLab from source or using the cookbook
# if you've installed GitLab from source
sudo -u git -H bundle exec rake gitlab:backup:create RAILS_ENV=production
```
......@@ -147,7 +147,7 @@ You can only restore a backup to exactly the same version of GitLab that you cre
# Omnibus package installation
sudo gitlab-rake gitlab:backup:restore
# installation from source or cookbook
# installation from source
bundle exec rake gitlab:backup:restore RAILS_ENV=production
```
......@@ -192,7 +192,7 @@ Deleting tmp directories...[DONE]
For Omnibus package installations, see https://gitlab.com/gitlab-org/omnibus-gitlab/blob/master/README.md#scheduling-a-backup .
For installation from source or cookbook:
For installation from source:
```
cd /home/git/gitlab
sudo -u git -H editor config/gitlab.yml # Enable keep_time in the backup section to automatically delete old backups
......@@ -214,19 +214,19 @@ This is recommended to reduce cron spam.
If your GitLab server contains a lot of Git repository data you may find the GitLab backup script to be too slow.
In this case you can consider using filesystem snapshots as part of your backup strategy.
Example: Amazone EBS
Example: Amazon EBS
> A GitLab server using omnibus-gitlab hosted on Amazon AWS.
> An EBS drive containing an ext4 filesystem is mounted at `/var/opt/gitlab`.
> In this case you could make an application backup by taking an EBS snapshot.
> The backup includes all repositories, uploads and Postgres data.
Example: LVM snapshots + Rsync
Example: LVM snapshots + rsync
> A GitLab server using omnibus-gitlab, with an LVM logical volume mounted at `/var/opt/gitlab`.
> Replicating the `/var/opt/gitlab` directory usign Rsync would not be reliable because too many files would change while Rsync is running.
> Replicating the `/var/opt/gitlab` directory using rsync would not be reliable because too many files would change while rsync is running.
> Instead of rsync-ing `/var/opt/gitlab`, we create a temporary LVM snapshot, which we mount as a read-only filesystem at `/mnt/gitlab_backup`.
> Now we can have a longer running Rsync job which will create a consistent replica on the remote server.
> Now we can have a longer running rsync job which will create a consistent replica on the remote server.
> The replica includes all repositories, uploads and Postgres data.
If you are running GitLab on a virtualized server you can possibly also create VM snapshots of the entire GitLab server.
......
......@@ -8,7 +8,7 @@ Remove namespaces(dirs) from `/home/git/repositories` if they don't exist in Git
# omnibus-gitlab
sudo gitlab-rake gitlab:cleanup:dirs
# installation from source or cookbook
# installation from source
bundle exec rake gitlab:cleanup:dirs RAILS_ENV=production
```
......@@ -18,6 +18,6 @@ Remove repositories (global only for now) from `/home/git/repositories` if they
# omnibus-gitlab
sudo gitlab-rake gitlab:cleanup:repos
# installation from source or cookbook
# installation from source
bundle exec rake gitlab:cleanup:repos RAILS_ENV=production
```
......@@ -6,7 +6,7 @@ This command will enable the namespaces feature introduced in v4.0. It will move
Note:
- Because the **repository location will change**, you will need to **update all your git url's** to point to the new location.
- Because the **repository location will change**, you will need to **update all your git URLs** to point to the new location.
- Username can be changed at [Profile / Account](/profile/account)
**Example:**
......
......@@ -19,19 +19,26 @@ your repositories are located by looking at `config/gitlab.yml` under the `gitla
New folder needs to have git user ownership and read/write/execute access for git user and its group:
```
$ mkdir new_group
$ chown git:git new_group
$ chmod 770 new_group
sudo -u git mkdir /var/opt/gitlab/git-data/repositories/new_group
```
If you are using an installation from source, replace `/var/opt/gitlab/git-data`
with `/home/git`.
### Copy your bare repositories inside this newly created folder:
```
$ cp -r /old/git/foo.git/ /home/git/repositories/new_group/
sudo cp -r /old/git/foo.git /var/opt/gitlab/git-data/repositories/new_group/
# Do this once when you are done copying git repositories
sudo chown -R git:git /var/opt/gitlab/git-data/repositories/new_group/
```
`foo.git` needs to be owned by the git user and git users group.
If you are using an installation from source, replace `/var/opt/gitlab/git-data`
with `/home/git`.
### Run the command below depending on your type of installation:
#### Omnibus Installation
......
......@@ -8,7 +8,7 @@ This command gathers information about your GitLab installation and the System i
# omnibus-gitlab
sudo gitlab-rake gitlab:env:info
# installation from source or cookbook
# installation from source
bundle exec rake gitlab:env:info RAILS_ENV=production
```
......@@ -16,27 +16,28 @@ Example output:
```
System information
System: Debian 6.0.7
System: Debian 7.8
Current User: git
Using RVM: no
Ruby Version: 2.0.0-p481
Gem Version: 1.8.23
Bundler Version:1.3.5
Rake Version: 10.0.4
Ruby Version: 2.1.5p273
Gem Version: 2.4.3
Bundler Version: 1.7.6
Rake Version: 10.3.2
Sidekiq Version: 2.17.8
GitLab information
Version: 5.1.0.beta2
Revision: 4da8b37
Version: 7.7.1
Revision: 41ab9e1
Directory: /home/git/gitlab
DB Adapter: mysql2
URL: http://example.com
HTTP Clone URL: http://example.com/some-project.git
SSH Clone URL: git@example.com:some-project.git
DB Adapter: postgresql
URL: https://gitlab.example.com
HTTP Clone URL: https://gitlab.example.com/some-project.git
SSH Clone URL: git@gitlab.example.com:some-project.git
Using LDAP: no
Using Omniauth: no
GitLab Shell
Version: 1.2.0
Version: 2.4.1
Repositories: /home/git/repositories/
Hooks: /home/git/gitlab-shell/hooks/
Git: /usr/bin/git
......@@ -59,7 +60,7 @@ You may also have a look at our [Trouble Shooting Guide](https://github.com/gitl
# omnibus-gitlab
sudo gitlab-rake gitlab:check
# installation from source or cookbook
# installation from source
bundle exec rake gitlab:check RAILS_ENV=production
```
......@@ -127,7 +128,6 @@ sudo chmod u+rwx,g=rx,o-rwx /home/git/gitlab-satellites
In some case it is necessary to rebuild the `authorized_keys` file.
For Omnibus-packages:
```
sudo gitlab-rake gitlab:shell:setup
......@@ -143,6 +143,36 @@ sudo -u git -H bundle exec rake gitlab:shell:setup RAILS_ENV=production
This will rebuild an authorized_keys file.
You will lose any data stored in authorized_keys file.
Do you want to continue (yes/no)? yes
```
## Clear redis cache
If for some reason the dashboard shows wrong information you might want to
clear Redis' cache.
For Omnibus-packages:
```
sudo gitlab-rake cache:clear
```
For installations from source:
```
cd /home/git/gitlab
sudo -u git -H bundle exec rake cache:clear RAILS_ENV=production
```
## Precompile the assets
............................
Sometimes during version upgrades you might end up with some wrong CSS or
missing some icons. In that case, try to precompile the assets again.
For Omnibus-packages:
```
sudo gitlab-rake assets:precompile
```
For installations from source:
```
cd /home/git/gitlab
sudo -u git -H bundle exec rake assets:precompile RAILS_ENV=production
```
......@@ -6,7 +6,7 @@
# omnibus-gitlab
sudo gitlab-rake gitlab:import:user_to_projects[username@domain.tld]
# installation from source or cookbook
# installation from source
bundle exec rake gitlab:import:user_to_projects[username@domain.tld] RAILS_ENV=production
```
......@@ -20,7 +20,7 @@ Notes:
# omnibus-gitlab
sudo gitlab-rake gitlab:import:all_users_to_all_projects
# installation from source or cookbook
# installation from source
bundle exec rake gitlab:import:all_users_to_all_projects RAILS_ENV=production
```
......@@ -30,7 +30,7 @@ bundle exec rake gitlab:import:all_users_to_all_projects RAILS_ENV=production
# omnibus-gitlab
sudo gitlab-rake gitlab:import:user_to_groups[username@domain.tld]
# installation from source or cookbook
# installation from source
bundle exec rake gitlab:import:user_to_groups[username@domain.tld] RAILS_ENV=production
```
......@@ -44,6 +44,6 @@ Notes:
# omnibus-gitlab
sudo gitlab-rake gitlab:import:all_users_to_all_groups
# installation from source or cookbook
# installation from source
bundle exec rake gitlab:import:all_users_to_all_groups RAILS_ENV=production
```
......@@ -4,42 +4,42 @@
# omnibus-gitlab
sudo gitlab-rake gitlab:web_hook:add URL="http://example.com/hook"
# source installations or cookbook
# source installations
bundle exec rake gitlab:web_hook:add URL="http://example.com/hook" RAILS_ENV=production
## Add a web hook for projects in a given **NAMESPACE**:
# omnibus-gitlab
sudo gitlab-rake gitlab:web_hook:add URL="http://example.com/hook" NAMESPACE=acme
# source installations or cookbook
# source installations
bundle exec rake gitlab:web_hook:add URL="http://example.com/hook" NAMESPACE=acme RAILS_ENV=production
## Remove a web hook from **ALL** projects using:
# omnibus-gitlab
sudo gitlab-rake gitlab:web_hook:rm URL="http://example.com/hook"
# source installations or cookbook
# source installations
bundle exec rake gitlab:web_hook:rm URL="http://example.com/hook" RAILS_ENV=production
## Remove a web hook from projects in a given **NAMESPACE**:
# omnibus-gitlab
sudo gitlab-rake gitlab:web_hook:rm URL="http://example.com/hook" NAMESPACE=acme
# source installations or cookbook
# source installations
bundle exec rake gitlab:web_hook:rm URL="http://example.com/hook" NAMESPACE=acme RAILS_ENV=production
## List **ALL** web hooks:
# omnibus-gitlab
sudo gitlab-rake gitlab:web_hook:list
# source installations or cookbook
# source installations
bundle exec rake gitlab:web_hook:list RAILS_ENV=production
## List the web hooks from projects in a given **NAMESPACE**:
# omnibus-gitlab
sudo gitlab-rake gitlab:web_hook:list NAMESPACE=/
# source installations or cookbook
# source installations
bundle exec rake gitlab:web_hook:list NAMESPACE=/ RAILS_ENV=production
> Note: `/` is the global namespace.
......@@ -104,7 +104,7 @@ bundle exec rake release["x.x.0.rc1"]
```
Now developers can use master for merging new features.
So you should use stable branch for future code chages related to release.
So you should use stable branch for future code changes related to release.
### 5. Release GitLab CI RC1
......
......@@ -207,7 +207,7 @@ __3. Tweet to blog__
Send out a tweet to share the good news with the world.
List the most important features and link to the blog post.
Proposed tweet "Release of GitLab X.X & CI Y.Y! FEATURE, FEATURE and FEATURE <link-to-blogpost> #gitlab"
Proposed tweet "Release of GitLab X.X & CI Y.Y! FEATURE, FEATURE and FEATURE &lt;link-to-blog-post&gt; #gitlab"
Consider creating a post on Hacker News.
......
......@@ -4,6 +4,6 @@ Git is a distributed version control system (DVCS).
This means that everyone that works with the source code has a local copy of the complete repository.
In GitLab every project member that is not a guest (so reporters, developers and masters) can clone the repository to get a local copy.
After obtaining this local copy the user can upload the full repository anywhere, including another project under their control or another server.
The consequense is that you can't build access controls that prevent the intentional sharing of source code by users that have access to the source code.
The consequence is that you can't build access controls that prevent the intentional sharing of source code by users that have access to the source code.
This is an inherent feature of a DVCS and all git management systems have this limitation.
Obviously you can take steps to prevent unintentional sharing and information destruction, this is why only some people are allowed to invite others and nobody can force push a protected branch.
# SSH
- [Deploy keys](deploy_keys.md)
- [SSH](ssh.md)
## SSH keys
An SSH key allows you to establish a secure connection between your
computer and GitLab.
Before generating an SSH key, check if your system already has one by
running `cat ~/.ssh/id_rsa.pub`. If you see a long string starting with
`ssh-rsa` or `ssh-dsa`, you can skip the ssh-keygen step.
To generate a new SSH key, just open your terminal and use code below. The
ssh-keygen command prompts you for a location and filename to store the key
pair and for a password. When prompted for the location and filename, you
can press enter to use the default.
It is a best practice to use a password for an SSH key, but it is not
required and you can skip creating a password by pressing enter. Note that
the password you choose here can't be altered or retrieved.
```bash
ssh-keygen -t rsa -C "$your_email"
```
Use the code below to show your public key.
```bash
cat ~/.ssh/id_rsa.pub
```
Copy-paste the key to the 'My SSH Keys' section under the 'SSH' tab in your
user profile. Please copy the complete key starting with `ssh-` and ending
with your username and host.
Use code below to copy your public key to the clipboard. Depending on your
OS you'll need to use a different command:
**Windows:**
```bash
clip < ~/.ssh/id_rsa.pub
```
**Mac:**
```bash
pbcopy < ~/.ssh/id_rsa.pub
```
**Linux (requires xclip):**
```bash
xclip -sel clip < ~/.ssh/id_rsa.pub
```
## Deploy keys
Deploy keys allow read-only access to multiple projects with a single SSH
key.
This is really useful for cloning repositories to your Continuous
Integration (CI) server. By using deploy keys, you don't have to setup a
dummy user account.
If you are a project master or owner, you can add a deploy key in the
project settings under the section 'Deploy Keys'. Press the 'New Deploy
Key' button and upload a public SSH key. After this, the machine that uses
the corresponding private key has read-only access to the project.
You can't add the same deploy key twice with the 'New Deploy Key' option.
If you want to add the same key to another project, please enable it in the
list that says 'Deploy keys from projects available to you'. All the deploy
keys of all the projects you have access to are available. This project
access can happen through being a direct member of the projecti, or through
a group. See `def accessible_deploy_keys` in `app/models/user.rb` for more
information.
# Deploy keys
Deploy keys allow read-only access one or multiple projects with a single SSH key.
This is really useful for cloning repositories to your Continuous Integration (CI) server. By using a deploy keys you don't have to setup a dummy user account.
If you are a project master or owner you can add a deploy key in the project settings under the section Deploy Keys. Press the 'New Deploy Key' button and upload a public ssh key. After this the machine that uses the corresponding private key has read-only access to the project.
You can't add the same deploy key twice with the 'New Deploy Key' option. If you want to add the same key to another project please enable it in the list that says 'Deploy keys from projects available to you'. All the deploy keys of all the projects you have access to are available. This project access can happen through being a direct member of the project or through a group. See `def accessible_deploy_keys` in `app/models/user.rb` for more information.
# SSH keys
SSH key allows you to establish a secure connection between your computer and GitLab
Before generating an SSH key, check if your system already has one by running `cat ~/.ssh/id_rsa.pub` If your see a long string starting with `ssh-rsa` or `ssh-dsa`, you can skip the ssh-keygen step.
To generate a new SSH key just open your terminal and use code below. The ssh-keygen command prompts you for a location and filename to store the key pair and for a password. When prompted for the location and filename you can press enter to use the default.
It is a best practice to use a password for an SSH key but it is not required and you can skip creating a password by pressing enter.
Note that the password you choose here can't be altered or retrieved.
```bash
ssh-keygen -t rsa -C "$your_email"
```
Use the code below to show your public key.
```bash
cat ~/.ssh/id_rsa.pub
```
Copy-paste the key to the 'My SSH Keys' section under the 'SSH' tab in your user profile. Please copy the complete key starting with `ssh-` and ending with your username and host.
Use code below to copy your public key to the clipboard. Depending on your OS you'll need to use a different command:
**Windows:**
```bash
clip < ~/.ssh/id_rsa.pub
```
**Mac:**
```bash
pbcopy < ~/.ssh/id_rsa.pub
```
**Linux (requires xclip):**
```bash
xclip -sel clip < ~/.ssh/id_rsa.pub
```
......@@ -15,8 +15,8 @@ System hooks can be used, e.g. for logging or changing information in a LDAP ser
"name": "StoreCloud",
"owner_email": "johnsmith@gmail.com",
"owner_name": "John Smith",
"path": "stormcloud",
"path_with_namespace": "jsmith/stormcloud",
"path": "storecloud",
"path_with_namespace": "jsmith/storecloud",
"project_id": 74,
"project_visibility": "private",
}
......@@ -126,10 +126,10 @@ System hooks can be used, e.g. for logging or changing information in a LDAP ser
{
"created_at": "2012-07-21T07:30:54Z",
"event_name": "group_create",
"name": "StormCloud",
"name": "StoreCloud",
"owner_email": "johnsmith@gmail.com",
"owner_name": "John Smith",
"path": "stormcloud",
"path": "storecloud",
"group_id": 78
}
```
......
......@@ -22,29 +22,29 @@ sudo -u gitlab bundle exec rake db:migrate RAILS_ENV=production
# !!! Config should be replaced with a new one. Check it after replace
cp config/gitlab.yml.example config/gitlab.yml
# update gitolite hooks
# update Gitolite hooks
# GITOLITE v2:
# Gitolite v2:
sudo cp ./lib/hooks/post-receive /home/git/share/gitolite/hooks/common/post-receive
sudo chown git:git /home/git/share/gitolite/hooks/common/post-receive
# GITOLITE v3:
# Gitolite v3:
sudo cp ./lib/hooks/post-receive /home/git/.gitolite/hooks/common/post-receive
sudo chown git:git /home/git/.gitolite/hooks/common/post-receive
# set valid path to hooks in gitlab.yml in git_host section
# like this
git_host:
# gitolite 2
# Gitolite 2
hooks_path: /home/git/share/gitolite/hooks
# gitolite 3
# Gitolite 3
hooks_path: /home/git/.gitolite/hooks/
# Make some changes to gitolite config
# Make some changes to Gitolite config
# For more information visit https://github.com/gitlabhq/gitlabhq/pull/1719
# gitolite v2
# Gitolite v2
sudo -u git -H sed -i 's/\(GL_GITCONFIG_KEYS\s*=>*\s*\).\{2\}/\\1"\.\*"/g' /home/git/.gitolite.rc
# gitlite v3
......
......@@ -41,8 +41,8 @@ git checkout v1.1.0
# copy config
cp config.yml.example config.yml
# change url to GitLab instance
# ! make sure url end with '/' like 'https://gitlab.example/'
# change URL to GitLab instance
# ! make sure the URL ends with '/' like 'https://gitlab.example/'
vim config.yml
# rewrite hooks
......@@ -111,7 +111,7 @@ sudo chmod -R u+rwX /home/git/gitlab/tmp/pids
```
## 6. Update init.d script and nginx config
## 6. Update init.d script and Nginx config
```bash
# init.d
......@@ -123,7 +123,7 @@ sudo chmod +x /etc/init.d/gitlab
sudo -u git -H cp /home/git/gitlab/config/unicorn.rb /home/git/gitlab/config/unicorn.rb.old
sudo -u git -H cp /home/git/gitlab/config/unicorn.rb.example /home/git/gitlab/config/unicorn.rb
#nginx
# Nginx
# Replace path from '/home/gitlab/' to '/home/git/'
sudo vim /etc/nginx/sites-enabled/gitlab
sudo service nginx restart
......@@ -137,7 +137,7 @@ sudo service gitlab start
# check if unicorn and sidekiq started
# If not try to logout, also check replaced path from '/home/gitlab/' to '/home/git/'
# in nginx, unicorn, init.d etc
# in Nginx, unicorn, init.d etc
ps aux | grep unicorn
ps aux | grep sidekiq
......
......@@ -40,7 +40,7 @@ sudo -u git -H bundle exec rake gitlab:backup:create RAILS_ENV=production
The migrations in this update are very sensitive to incomplete or inconsistent data. If you have a long-running GitLab installation and some of the previous upgrades did not work out 100% correct this may bite you now. The following can help you have a more smooth upgrade.
### Find projets with invalid project names
### Find projects with invalid project names
#### MySQL
Login to MySQL:
......
......@@ -10,7 +10,7 @@ GitLab 6.0 is affected by critical security vulnerabilities CVE-2013-4490 and CV
The root (global) namespace for projects is deprecated.
So you need to move all your global projects under groups or users manually before update or they will be automatically moved to the project owner namespace during the update. When a project is moved all its members will receive an email with instructions how to update their git remote url. Please make sure you disable sending email when you do a test of the upgrade.
So you need to move all your global projects under groups or users manually before update or they will be automatically moved to the project owner namespace during the update. When a project is moved all its members will receive an email with instructions how to update their git remote URL. Please make sure you disable sending email when you do a test of the upgrade.
### Teams
......
......@@ -35,7 +35,7 @@ sudo -u git -H git checkout v1.7.9 # Addresses multiple critical security vulner
## 4. Install additional packages
```bash
# Add support for lograte for better log file handling
# Add support for logrotate for better log file handling
sudo apt-get install logrotate
```
......
......@@ -84,11 +84,14 @@ sudo -u git -H git checkout 7-7-stable-ee
## 4. Install additional packages
```bash
# Add support for lograte for better log file handling
# Add support for logrotate for better log file handling
sudo apt-get install logrotate
# Install pkg-config and cmake, which is needed for the latest versions of rugged
sudo apt-get install pkg-config cmake
# Install Kerberos header files, which are needed for GitLab EE Kerberos support
sudo apt-get install libkrb5-dev
```
## 5. Configure Redis to use sockets
......@@ -219,13 +222,13 @@ mysql -u root -p
# Convert all tables to use the InnoDB storage engine (added in GitLab 6.8)
SELECT CONCAT('ALTER TABLE gitlabhq_production.', table_name, ' ENGINE=InnoDB;') AS 'Copy & run these SQL statements:' FROM information_schema.tables WHERE table_schema = 'gitlabhq_production' AND `ENGINE` <> 'InnoDB' AND `TABLE_TYPE` = 'BASE TABLE';
# If previous query returned results, copy & run all outputed SQL statements
# If previous query returned results, copy & run all shown SQL statements
# Convert all tables to correct character set
SET foreign_key_checks = 0;
SELECT CONCAT('ALTER TABLE gitlabhq_production.', table_name, ' CONVERT TO CHARACTER SET utf8 COLLATE utf8_general_ci;') AS 'Copy & run these SQL statements:' FROM information_schema.tables WHERE table_schema = 'gitlabhq_production' AND `TABLE_COLLATION` <> 'utf8_unicode_ci' AND `TABLE_TYPE` = 'BASE TABLE';
# If previous query returned results, copy & run all outputed SQL statements
# If previous query returned results, copy & run all shown SQL statements
# turn foreign key checks back on
SET foreign_key_checks = 1;
......
......@@ -114,13 +114,13 @@ mysql -u root -p
# Convert all tables to use the InnoDB storage engine (added in GitLab 6.8)
SELECT CONCAT('ALTER TABLE gitlabhq_production.', table_name, ' ENGINE=InnoDB;') AS 'Copy & run these SQL statements:' FROM information_schema.tables WHERE table_schema = 'gitlabhq_production' AND `ENGINE` <> 'InnoDB' AND `TABLE_TYPE` = 'BASE TABLE';
# If previous query returned results, copy & run all outputed SQL statements
# If previous query returned results, copy & run all shown SQL statements
# Convert all tables to correct character set
SET foreign_key_checks = 0;
SELECT CONCAT('ALTER TABLE gitlabhq_production.', table_name, ' CONVERT TO CHARACTER SET utf8 COLLATE utf8_general_ci;') AS 'Copy & run these SQL statements:' FROM information_schema.tables WHERE table_schema = 'gitlabhq_production' AND `TABLE_COLLATION` <> 'utf8_unicode_ci' AND `TABLE_TYPE` = 'BASE TABLE';
# If previous query returned results, copy & run all outputed SQL statements
# If previous query returned results, copy & run all shown SQL statements
# turn foreign key checks back on
SET foreign_key_checks = 1;
......
......@@ -37,7 +37,7 @@ sudo -u git -H git checkout 7-7-stable-ee
```bash
cd /home/git/gitlab-shell
sudo -u git -H git fetch
sudo -u git -H git checkout v2.4.1
sudo -u git -H git checkout v2.4.2
```
### 4. Install libs, migrations, etc.
......@@ -101,8 +101,8 @@ If all items are green, then congratulations upgrade is complete!
### 8. GitHub settings (if applicable)
If you are using GitHub as an OAuth provider for authentication, you should change the callback url so that it
only contains a root url (ex. `https://gitlab.example.com/`)
If you are using GitHub as an OAuth provider for authentication, you should change the callback URL so that it
only contains a root URL (ex. `https://gitlab.example.com/`)
## Things went south? Revert to previous version (7.6)
......
......@@ -17,4 +17,4 @@ Depending on the installation method and your GitLab version, there are multiple
## Miscellaneous
- [MySQL to PostgreSQL](mysql_to_postgresql.md) guides you through migrating your database from MySQL to PostrgreSQL.
- [MySQL to PostgreSQL](mysql_to_postgresql.md) guides you through migrating your database from MySQL to PostgreSQL.
......@@ -11,3 +11,4 @@
- [Migrating from SVN to GitLab](migrating_from_svn.md)
- [Project importing from GitHub to GitLab](import_projects_from_github.md)
- [Protected branches](protected_branches.md)
- [Web Editor](web_editor.md)
......@@ -43,7 +43,7 @@ Since most tools automatically make the master branch the default one and displa
The second problem of git flow is the complexity introduced by the hotfix and release branches.
These branches can be a good idea for some organizations but are overkill for the vast majority of them.
Nowadays most organizations practice continuous delivery which means that your default branch can be deployed.
This means that hotfixed and release branches can be prevented including all the ceremony they introduce.
This means that hotfix and release branches can be prevented including all the ceremony they introduce.
An example of this ceremony is the merging back of release branches.
Though specialized tools do exist to solve this, they require documentation and add complexity.
Frequently developers make a mistake and for example changes are only merged into master and not into the develop branch.
......@@ -95,12 +95,12 @@ An 'extreme' version of environment branches are setting up an environment for e
## Release branches with GitLab flow
![Master and multiple release branches that vary in length with cherrypicks from master](release_branches.png)
![Master and multiple release branches that vary in length with cherry-picks from master](release_branches.png)
Only in case you need to release software to the outside world you need to work with release branches.
In this case, each branch contains a minor version (2-3-stable, 2-4-stable, etc.).
The stable branch uses master as a starting point and is created as late as possible.
By branching as late as possible you minimize the time you have to apply bugfixes to multiple branches.
By branching as late as possible you minimize the time you have to apply bug fixes to multiple branches.
After a release branch is announced, only serious bug fixes are included in the release branch.
If possible these bug fixes are first merged into master and then cherry-picked into the release branch.
This way you can't forget to cherry-pick them into master and encounter the same bug on subsequent releases.
......@@ -177,7 +177,7 @@ In GitLab this creates a comment in the issue that the merge requests mentions t
And the merge request shows the linked issues.
These issues are closed once code is merged into the default branch.
If you only want to make the reference without closing the issue you can also just mention it: "Ducktyping is preferred. #12".
If you only want to make the reference without closing the issue you can also just mention it: "Duck typing is preferred. #12".
If you have an issue that spans across multiple repositories, the best thing is to create an issue for each repository and link all issues to a parent issue.
......
......@@ -3,7 +3,7 @@
SVN stands for Subversion and is a version control system (VCS).
Git is a distributed version control system.
There are some major differences between the two, for more information consult your favourite search engine.
There are some major differences between the two, for more information consult your favorite search engine.
Git has tools for migrating SVN repositories to git, namely `git svn`. You can read more about this at
[git documentation pages](http://git-scm.com/book/en/Git-and-Other-Systems-Git-and-Subversion).
......
......@@ -24,14 +24,14 @@ Each of these settings have levels of notification:
#### Global Settings
Global Settings are at the bottom of the hierarchy.
Any setting set here will be overriden by a setting at the group or a project level.
Any setting set here will be overridden by a setting at the group or a project level.
Group or Project settings can use `global` notification setting which will then use
anything that is set at Global Settings.
#### Group Settings
Group Settings are taking presedence over Global Settings but are on a level below Project Settings.
Group Settings are taking precedence over Global Settings but are on a level below Project Settings.
This means that you can set a different level of notifications per group while still being able
to have a finer level setting per project.
Organization like this is suitable for users that belong to different groups but don't have the
......@@ -39,7 +39,7 @@ same need for being notified for every group they are member of.
#### Project Settings
Project Settings are at the top level and any setting placed at this level will take presedence of any
Project Settings are at the top level and any setting placed at this level will take precedence of any
other setting.
This is suitable for users that have different needs for notifications per project basis.
......
# GitLab Web Editor
In GitLab you can create new files and edit existing files using our web editor.
This is especially useful if you don't have access to a command line or you just want to do a quick fix.
You can easily access the web editor, depending on the context.
Let's start from newly created project.
Click on `Add a file`
to create the first file and open it in the web editor.
![web editor 1](web_editor/empty_project.png)
Fill in a file name, some content, a commit message and press the commit button.
The file will be saved to the repository.
![web editor 2](web_editor/new_file.png)
You can edit any text file in a repository by pressing the edit button, when
viewing the file.
![web editor 3](web_editor/show_file.png)
Editing a file is almost the same as creating a new file,
with as addition the ability to preview your changes in a separate tab.
![web editor 3](web_editor/edit_file.png)
......@@ -11,7 +11,7 @@ RUN apt-get update -q \
# If the Omnibus package version below is outdated please contribute a merge request to update it.
# If you run GitLab Enterprise Edition point it to a location where you have downloaded it.
RUN TMP_FILE=$(mktemp); \
wget -q -O $TMP_FILE https://downloads-packages.s3.amazonaws.com/ubuntu-14.04/gitlab_7.6.2-omnibus.5.3.0.ci.1-1_amd64.deb \
wget -q -O $TMP_FILE https://downloads-packages.s3.amazonaws.com/ubuntu-14.04/gitlab_7.7.2-omnibus.5.4.2.ci-1_amd64.deb \
&& dpkg -i $TMP_FILE \
&& rm -f $TMP_FILE
......
......@@ -34,7 +34,7 @@ Feature: Project Source Browse Files
Then I am redirected to the new file
And I should see its new content
@javascript
@javascript @tricky
Scenario: I can create file in empty repo
Given I own an empty project
And I visit my empty project page
......
......@@ -13,15 +13,15 @@ Feature: Search
And project has issues
When I search for "Foo"
And I click "Issues" link
Then I should see "Foo" link
And I should not see "Bar" link
Then I should see "Foo" link in the search results
And I should not see "Bar" link in the search results
Scenario: I should see merge requests I am looking for
And project has merge requests
When I search for "Foo"
When I click "Merge requests" link
Then I should see "Foo" link
And I should not see "Bar" link
Then I should see "Foo" link in the search results
And I should not see "Bar" link in the search results
Scenario: I should see project code I am looking for
When I click project "Shop" link
......@@ -33,14 +33,14 @@ Feature: Search
When I click project "Shop" link
And I search for "Foo"
And I click "Issues" link
Then I should see "Foo" link
And I should not see "Bar" link
Then I should see "Foo" link in the search results
And I should not see "Bar" link in the search results
Scenario: I should see project merge requests
And project has merge requests
When I click project "Shop" link
And I search for "Foo"
And I click "Merge requests" link
Then I should see "Foo" link
And I should not see "Bar" link
Then I should see "Foo" link in the search results
And I should not see "Bar" link in the search results
......@@ -41,7 +41,7 @@ class Spinach::Features::AdminGroups < Spinach::FeatureSteps
within "#new_team_member" do
select "Reporter", from: "access_level"
end
click_button "Add users into group"
click_button "Add users to group"
end
step 'I should see "John Doe" in team list in every project as "Reporter"' do
......
......@@ -34,7 +34,7 @@ class Spinach::Features::Groups < Spinach::FeatureSteps
select2(user.id, from: "#user_ids", multiple: true)
select "Reporter", from: "access_level"
end
click_button "Add users into group"
click_button "Add users to group"
end
step 'I should see user "John Doe" in team list' do
......
......@@ -59,11 +59,11 @@ class Spinach::Features::Search < Spinach::FeatureSteps
create(:merge_request, :simple, title: "Bar", source_project: project, target_project: project)
end
step 'I should see "Foo" link' do
page.should have_link "Foo"
step 'I should see "Foo" link in the search results' do
find(:css, '.search-results').should have_link 'Foo'
end
step 'I should not see "Bar" link' do
page.should_not have_link "Bar"
step 'I should not see "Bar" link in the search results' do
find(:css, '.search-results').should_not have_link 'Bar'
end
end
......@@ -6,7 +6,7 @@ module API
version 'v3', using: :path
rescue_from ActiveRecord::RecordNotFound do
rack_response({'message' => '404 Not found'}.to_json, 404)
rack_response({ 'message' => '404 Not found' }.to_json, 404)
end
rescue_from :all do |exception|
......@@ -19,7 +19,7 @@ module API
message << " " << trace.join("\n ")
API.logger.add Logger::FATAL, message
rack_response({'message' => '500 Internal Server Error'}, 500)
rack_response({ 'message' => '500 Internal Server Error' }, 500)
end
format :json
......
......@@ -47,16 +47,12 @@ module APIGuard
case validate_access_token(access_token, scopes)
when Oauth2::AccessTokenValidationService::INSUFFICIENT_SCOPE
raise InsufficientScopeError.new(scopes)
when Oauth2::AccessTokenValidationService::EXPIRED
raise ExpiredError
when Oauth2::AccessTokenValidationService::REVOKED
raise RevokedError
when Oauth2::AccessTokenValidationService::VALID
@current_user = User.find(access_token.resource_owner_id)
end
end
end
......@@ -120,8 +116,9 @@ module APIGuard
end
def oauth2_bearer_token_error_handler
Proc.new {|e|
response = case e
Proc.new do |e|
response =
case e
when MissingTokenError
Rack::OAuth2::Server::Resource::Bearer::Unauthorized.new
......@@ -146,11 +143,11 @@ module APIGuard
Rack::OAuth2::Server::Resource::Bearer::Forbidden.new(
:insufficient_scope,
Rack::OAuth2::Server::Resource::ErrorMethods::DEFAULT_DESCRIPTION[:insufficient_scope],
{ :scope => e.scopes})
{ scope: e.scopes })
end
response.finish
}
end
end
end
......
......@@ -60,7 +60,7 @@ module API
expose :path, :path_with_namespace
expose :issues_enabled, :merge_requests_enabled, :wiki_enabled, :snippets_enabled, :created_at, :last_activity_at
expose :namespace
expose :forked_from_project, using: Entities::ForkedFromProject, :if => lambda{ | project, options | project.forked? }
expose :forked_from_project, using: Entities::ForkedFromProject, if: lambda{ | project, options | project.forked? }
end
class ProjectMember < UserBasic
......@@ -157,6 +157,11 @@ module API
expose :state, :created_at, :updated_at
end
class RepoDiff < Grape::Entity
expose :old_path, :new_path, :a_mode, :b_mode, :diff
expose :new_file, :renamed_file, :deleted_file
end
class Milestone < ProjectEntity
expose :due_date
end
......@@ -176,6 +181,12 @@ module API
expose :milestone, using: Entities::Milestone
end
class MergeRequestChanges < MergeRequest
expose :diffs, as: :changes, using: Entities::RepoDiff do |compare, _|
compare.diffs
end
end
class SSHKey < Grape::Entity
expose :id, :title, :key, :created_at
end
......@@ -254,11 +265,6 @@ module API
expose :name, :color
end
class RepoDiff < Grape::Entity
expose :old_path, :new_path, :a_mode, :b_mode, :diff
expose :new_file, :renamed_file, :deleted_file
end
class Compare < Grape::Entity
expose :commit, using: Entities::RepoCommit do |compare, options|
Commit.decorate(compare.commits).last
......
......@@ -3,22 +3,6 @@ module API
before { authenticate! }
resource :groups do
helpers do
def find_group(id)
group = Group.find(id)
if can?(current_user, :read_group, group)
group
else
render_api_error!("403 Forbidden - #{current_user.username} lacks sufficient access to #{group.name}", 403)
end
end
def validate_access_level?(level)
Gitlab::Access.options_with_owner.values.include? level.to_i
end
end
# Get a list of group members viewable by the authenticated user.
#
# Example Request:
......
......@@ -4,22 +4,6 @@ module API
before { authenticate! }
resource :groups do
helpers do
def find_group(id)
group = Group.find(id)
if can?(current_user, :read_group, group)
group
else
render_api_error!("403 Forbidden - #{current_user.username} lacks sufficient access to #{group.name}", 403)
end
end
def validate_access_level?(level)
Gitlab::Access.options_with_owner.values.include? level.to_i
end
end
# Get a groups list
#
# Example Request:
......
......@@ -55,6 +55,21 @@ module API
end
end
def find_group(id)
begin
group = Group.find(id)
rescue ActiveRecord::RecordNotFound
group = Group.find_by!(path: id)
end
if can?(current_user, :read_group, group)
group
else
forbidden!("#{current_user.username} lacks sufficient "\
"access to #{group.name}")
end
end
def paginate(relation)
per_page = params[:per_page].to_i
paginated = relation.page(params[:page]).per(per_page)
......@@ -135,10 +150,16 @@ module API
errors
end
def validate_access_level?(level)
Gitlab::Access.options_with_owner.values.include? level.to_i
end
# error helpers
def forbidden!
render_api_error!('403 Forbidden', 403)
def forbidden!(reason = nil)
message = ['403 Forbidden']
message << " - #{reason}" if reason
render_api_error!(message.join(' '), 403)
end
def bad_request!(attribute)
......@@ -173,7 +194,7 @@ module API
end
def render_api_error!(message, status)
error!({'message' => message}, status)
error!({ 'message' => message }, status)
end
private
......
module API
# Internal access API
class Internal < Grape::API
before {
authenticate_by_gitlab_shell_token!
}
before { authenticate_by_gitlab_shell_token! }
namespace 'internal' do
# Check if git command is allowed to project
......
......@@ -75,6 +75,22 @@ module API
present merge_request, with: Entities::MergeRequest
end
# Show MR changes
#
# Parameters:
# id (required) - The ID of a project
# merge_request_id (required) - The ID of MR
#
# Example:
# GET /projects/:id/merge_request/:merge_request_id/changes
#
get ':id/merge_request/:merge_request_id/changes' do
merge_request = user_project.merge_requests.
find(params[:merge_request_id])
authorize! :read_merge_request, merge_request
present merge_request, with: Entities::MergeRequestChanges
end
# Create MR
#
# Parameters:
......
module API
# namespaces API
class Namespaces < Grape::API
before {
before do
authenticate!
authenticated_as_admin!
}
end
resource :namespaces do
# Get a namespaces list
......
......@@ -110,7 +110,7 @@ module API
unless team_member.nil?
team_member.destroy
else
{message: "Access revoked", id: params[:user_id].to_i}
{ message: "Access revoked", id: params[:user_id].to_i }
end
end
end
......
module API
# Hooks API
class SystemHooks < Grape::API
before {
before do
authenticate!
authenticated_as_admin!
}
end
resource :hooks do
# Get the list of system hooks
......
......@@ -11,6 +11,11 @@ module Gitlab
MASTER = 40
OWNER = 50
# Branch protection settings
PROTECTION_NONE = 0
PROTECTION_DEV_CAN_PUSH = 1
PROTECTION_FULL = 2
class << self
def values
options.values
......@@ -43,6 +48,18 @@ module Gitlab
master: MASTER,
}
end
def protection_options
{
"Not protected, developers and masters can (force) push and delete the branch" => PROTECTION_NONE,
"Partially protected, developers can also push but prevent all force pushes and deletion" => PROTECTION_DEV_CAN_PUSH,
"Fully protected, only masters can push and prevent all force pushes and deletion" => PROTECTION_FULL,
}
end
def protection_values
protection_options.values
end
end
def human_access
......
......@@ -154,7 +154,7 @@ module Grack
end
def render_not_found
[404, {"Content-Type" => "text/plain"}, ["Not Found"]]
[404, { "Content-Type" => "text/plain" }, ["Not Found"]]
end
end
end
......@@ -9,4 +9,3 @@ module Gitlab
end
end
end
......@@ -2,15 +2,15 @@ module Gitlab
class CommitsCalendar
attr_reader :timestamps
def initialize(repositories, user)
def initialize(projects, user)
@timestamps = {}
date_timestamps = []
repositories.select(&:exists?).reject(&:empty?).each do |raw_repository|
commits_log = raw_repository.commits_per_day_for_user(user)
date_timestamps << commits_log
projects.reject(&:forked?).each do |project|
date_timestamps << ProjectContributions.new(project, user).commits_log
end
# Sumarrize commits from all projects per days
date_timestamps = date_timestamps.inject do |collection, date|
collection.merge(date) { |k, old_v, new_v| old_v + new_v }
end
......@@ -21,5 +21,13 @@ module Gitlab
@timestamps[timestamp] = commits if timestamp
end
end
def starting_year
(Time.now - 1.year).strftime("%Y")
end
def starting_month
Date.today.strftime("%m").to_i
end
end
end
......@@ -12,6 +12,7 @@ module Gitlab
def fake_application_settings
OpenStruct.new(
default_projects_limit: Settings.gitlab['default_projects_limit'],
default_branch_protection: Settings.gitlab['default_branch_protection'],
signup_enabled: Settings.gitlab['signup_enabled'],
signin_enabled: Settings.gitlab['signin_enabled'],
gravatar_enabled: Settings.gravatar['enabled'],
......
......@@ -4,7 +4,7 @@ module Gitlab
include Enumerable
def parse(lines)
@lines = lines,
@lines = lines
lines_obj = []
line_obj_index = 0
line_old = 1
......
......@@ -12,4 +12,3 @@ module Gitlab
end
end
end
......@@ -180,8 +180,8 @@ module Gitlab
# we dont allow force push to protected branch
if forced_push?(project, oldrev, newrev)
:force_push_code_to_protected_branches
# and we dont allow remove of protected branch
elsif newrev == Gitlab::Git::BLANK_SHA
# and we dont allow remove of protected branch
:remove_protected_branches
elsif project.developers_can_push_to_protected_branch?(branch_name)
:push_code
......
......@@ -9,7 +9,7 @@ module Gitlab
end
def to_json
{status: @status, message: @message}.to_json
{ status: @status, message: @message }.to_json
end
end
end
......@@ -36,7 +36,7 @@ module Gitlab
def octo_client(access_token)
::Octokit.auto_paginate = true
::Octokit::Client.new(:access_token => access_token)
::Octokit::Client.new(access_token: access_token)
end
def gl_user_id(project, github_id)
......
......@@ -180,5 +180,3 @@ module Gitlab
end
end
end
......@@ -87,8 +87,10 @@ module Gitlab
end
def dn_matches_filter?(dn, filter)
ldap_search(base: dn, filter: filter,
scope: Net::LDAP::SearchScope_BaseObject, attributes: %w{dn}).any?
ldap_search(base: dn,
filter: filter,
scope: Net::LDAP::SearchScope_BaseObject,
attributes: %w{dn}).any?
end
def ldap_search(*args)
......
......@@ -40,12 +40,16 @@ module Gitlab
def update_user_attributes
gl_user.email = auth_hash.email
gl_user.identities.build(provider: auth_hash.provider, extern_uid: auth_hash.uid)
# Build new identity only if we dont have have same one
gl_user.identities.find_or_initialize_by(provider: auth_hash.provider,
extern_uid: auth_hash.uid)
gl_user
end
def changed?
gl_user.changed?
gl_user.changed? || gl_user.identities.any?(&:changed?)
end
def needs_blocking?
......
......@@ -44,7 +44,7 @@ module Gitlab
end
def default_options(options = {})
{raise: true, timeout: true}.merge(options)
{ raise: true, timeout: true }.merge(options)
end
def handle_exception(exception)
......
......@@ -13,7 +13,7 @@ module Gitlab
prepare_satellite!(repo)
# create target branch in satellite at the corresponding commit from bare repo
repo.git.checkout({raise: true, timeout: true, b: true}, ref, "origin/#{ref}")
repo.git.checkout({ raise: true, timeout: true, b: true }, ref, "origin/#{ref}")
# update the file in the satellite's working dir
file_path_in_satellite = File.join(repo.working_dir, file_path)
......@@ -36,7 +36,7 @@ module Gitlab
# push commit back to bare repo
# will raise CommandFailed when push fails
repo.git.push({raise: true, timeout: true}, :origin, ref)
repo.git.push({ raise: true, timeout: true }, :origin, ref)
# everything worked
true
......
......@@ -15,7 +15,7 @@ module Gitlab
prepare_satellite!(repo)
# create target branch in satellite at the corresponding commit from bare repo
repo.git.checkout({raise: true, timeout: true, b: true}, ref, "origin/#{ref}")
repo.git.checkout({ raise: true, timeout: true, b: true }, ref, "origin/#{ref}")
# update the file in the satellite's working dir
file_path_in_satellite = File.join(repo.working_dir, file_path)
......@@ -36,7 +36,7 @@ module Gitlab
# push commit back to bare repo
# will raise CommandFailed when push fails
repo.git.push({raise: true, timeout: true}, :origin, ref)
repo.git.push({ raise: true, timeout: true }, :origin, ref)
# everything worked
true
......
......@@ -19,7 +19,7 @@ module Gitlab
# skip this step if we want to add first file to empty repo
Satellite::PARKING_BRANCH
else
repo.git.checkout({raise: true, timeout: true, b: true}, ref, "origin/#{ref}")
repo.git.checkout({ raise: true, timeout: true, b: true }, ref, "origin/#{ref}")
ref
end
......@@ -47,7 +47,7 @@ module Gitlab
# push commit back to bare repo
# will raise CommandFailed when push fails
repo.git.push({raise: true, timeout: true}, :origin, "#{current_ref}:#{ref}")
repo.git.push({ raise: true, timeout: true }, :origin, "#{current_ref}:#{ref}")
# everything worked
true
......
......@@ -96,7 +96,7 @@ module Gitlab
in_locked_and_timed_satellite do |merge_repo|
prepare_satellite!(merge_repo)
update_satellite_source_and_target!(merge_repo)
patch = merge_repo.git.format_patch(default_options({stdout: true}), "origin/#{merge_request.target_branch}..source/#{merge_request.source_branch}")
patch = merge_repo.git.format_patch(default_options({ stdout: true }), "origin/#{merge_request.target_branch}..source/#{merge_request.source_branch}")
end
rescue Grit::Git::CommandFailed => ex
handle_exception(ex)
......@@ -138,7 +138,7 @@ module Gitlab
# merge the source branch into the satellite
# will raise CommandFailed when merge fails
repo.git.merge(default_options({no_ff: true}), "-m#{message}", "source/#{merge_request.source_branch}")
repo.git.merge(default_options({ no_ff: true }), "-m#{message}", "source/#{merge_request.source_branch}")
rescue Grit::Git::CommandFailed => ex
handle_exception(ex)
end
......@@ -159,7 +159,7 @@ module Gitlab
# git push remote master
def rebase_in_satellite!(repo)
update_satellite_source_and_target!(repo)
repo.git.checkout(default_options({b: true}), merge_request.source_branch, "source/#{merge_request.source_branch}")
repo.git.checkout(default_options({ b: true }), merge_request.source_branch, "source/#{merge_request.source_branch}")
output, status = popen(%W(git pull --rebase origin #{merge_request.target_branch}), repo.working_dir)
if status == 0
......@@ -181,7 +181,7 @@ module Gitlab
def update_satellite_source_and_target!(repo)
repo.remote_add('source', merge_request.source_project.repository.path_to_repo)
repo.remote_fetch('source')
repo.git.checkout(default_options({b: true}), merge_request.target_branch, "origin/#{merge_request.target_branch}")
repo.git.checkout(default_options({ b: true }), merge_request.target_branch, "origin/#{merge_request.target_branch}")
rescue Grit::Git::CommandFailed => ex
handle_exception(ex)
end
......
......@@ -98,13 +98,13 @@ module Gitlab
if heads.include? PARKING_BRANCH
repo.git.checkout({}, PARKING_BRANCH)
else
repo.git.checkout(default_options({b: true}), PARKING_BRANCH)
repo.git.checkout(default_options({ b: true }), PARKING_BRANCH)
end
# remove the parking branch from the list of heads ...
heads.delete(PARKING_BRANCH)
# ... and delete all others
heads.each { |head| repo.git.branch(default_options({D: true}), head) }
heads.each { |head| repo.git.branch(default_options({ D: true }), head) }
end
# Deletes all remotes except origin
......@@ -126,7 +126,7 @@ module Gitlab
end
def default_options(options = {})
{raise: true, timeout: true}.merge(options)
{ raise: true, timeout: true }.merge(options)
end
# Create directory for storing
......
......@@ -62,7 +62,7 @@ module Gitlab
end
def env
{'RAILS_ENV' => 'production'}
{ 'RAILS_ENV' => 'production' }
end
def upgrade
......
# Interface to the Redis-backed cache store used by the Repository model
class RepositoryCache
attr_reader :namespace, :backend
def initialize(namespace, backend = Rails.cache)
@namespace = namespace
@backend = backend
end
def cache_key(type)
"#{type}:#{namespace}"
end
def expire(key)
backend.delete(cache_key(key))
end
def fetch(key, &block)
backend.fetch(cache_key(key), &block)
end
end
......@@ -39,7 +39,7 @@ upstream gitlab {
## Redirects all HTTP traffic to the HTTPS host
server {
listen 0.0.0.0:80;
listen [::]:80 default_server;
listen [::]:80 ipv6only=on default_server;
server_name YOUR_SERVER_FQDN; ## Replace this with something like gitlab.example.com
server_tokens off; ## Don't show the nginx version number, a security best practice
return 301 https://$server_name$request_uri;
......@@ -51,7 +51,7 @@ server {
## HTTPS host
server {
listen 0.0.0.0:443 ssl;
listen [::]:443 ssl default_server;
listen [::]:443 ipv6only=on ssl default_server;
server_name YOUR_SERVER_FQDN; ## Replace this with something like gitlab.example.com
server_tokens off; ## Don't show the nginx version number, a security best practice
root /home/git/gitlab/public;
......
......@@ -2,6 +2,7 @@ namespace :gitlab do
desc "GITLAB | Run all tests"
task :test do
cmds = [
%W(rake rubocop),
%W(rake spinach),
%W(rake spec),
%W(rake jasmine:ci)
......
unless Rails.env.production?
require 'rubocop/rake_task'
RuboCop::RakeTask.new
end
......@@ -2,9 +2,15 @@ Rake::Task["spinach"].clear if Rake::Task.task_defined?('spinach')
desc "GITLAB | Run spinach"
task :spinach do
tags = if ENV['SEMAPHORE']
'~@tricky'
else
'~@semaphore'
end
cmds = [
%W(rake gitlab:setup),
%W(spinach),
%W(spinach --tags #{tags}),
]
run_commands(cmds)
end
......
......@@ -9,5 +9,5 @@ unless Rails.env.production?
require 'coveralls/rake/task'
Coveralls::RakeTask.new
desc "GITLAB | Run all tests on CI with simplecov"
task :test_ci => [:spinach, :spec, 'coveralls:push']
task :test_ci => [:rubocop, :spinach, :spec, 'coveralls:push']
end
......@@ -70,4 +70,13 @@ describe Projects::CommitController do
end
end
end
describe "#branches" do
it "contains branch and tags information" do
get :branches, project_id: project.to_param, id: commit.id
expect(assigns(:branches)).to include("master", "feature_conflict")
expect(assigns(:tags)).to include("v1.1.0")
end
end
end
......@@ -9,18 +9,18 @@ describe UsersController do
describe "GET #show" do
render_views
before do
get :show, username: user.username
end
it "renders the show template" do
get :show, username: user.username
expect(response.status).to eq(200)
expect(response).to render_template("show")
end
end
describe "GET #calendar" do
it "renders calendar" do
controller.prepend_view_path 'app/views/users'
expect(response).to render_template("_calendar")
get :calendar, username: user.username
expect(response).to render_template("calendar")
end
end
end
......
......@@ -26,6 +26,7 @@
# star_count :integer default(0), not null
# import_type :string(255)
# import_source :string(255)
# avatar :string(255)
#
FactoryGirl.define do
......
......@@ -6,7 +6,7 @@ describe 'Help Pages', feature: true do
login_as :user
end
it 'replace the variable $your_email with the email of the user' do
visit help_page_path(category: 'ssh', file: 'ssh.md')
visit help_page_path(category: 'ssh', file: 'README.md')
page.should have_content("ssh-keygen -t rsa -C \"#{@user.email}\"")
end
end
......
......@@ -65,7 +65,7 @@ describe "Issues", feature: true do
click_button "Save changes"
page.should have_content "Assignee: Select assignee"
page.should have_content 'Assignee: none'
issue.reload.assignee.should be_nil
end
end
......@@ -249,6 +249,7 @@ describe "Issues", feature: true do
click_button 'Update Issue'
page.should have_content "Milestone changed to #{milestone.title}"
page.should have_content "Milestone: #{milestone.title}"
has_select?('issue_assignee_id', :selected => milestone.title)
end
end
......@@ -287,7 +288,7 @@ describe "Issues", feature: true do
sleep 2 # wait for ajax stuff to complete
first('.user-result').click
page.should have_content "Assignee: Unassigned"
page.should have_content 'Assignee: none'
sleep 2 # wait for ajax stuff to complete
issue.reload.assignee.should be_nil
end
......
require 'spec_helper'
# Specs in this file have access to a helper object that includes
# the NavHelper. For example:
#
# describe NavHelper do
# describe "string concat" do
# it "concats two strings with spaces" do
# expect(helper.concat_strings("this","that")).to eq("this that")
# end
# end
# end
describe NavHelper do
describe '#nav_menu_collapsed?' do
it 'returns true when the nav is collapsed in the cookie' do
helper.request.cookies[:collapsed_nav] = 'true'
expect(helper.nav_menu_collapsed?).to eq true
end
it 'returns false when the nav is not collapsed in the cookie' do
helper.request.cookies[:collapsed_nav] = 'false'
expect(helper.nav_menu_collapsed?).to eq false
end
end
end
require 'spec_helper'
describe NotificationsHelper do
include FontAwesome::Rails::IconHelper
include IconsHelper
describe 'notification_icon' do
let(:notification) { double(disabled?: false, participating?: false, watch?: false) }
......
......@@ -13,6 +13,23 @@ describe Gitlab::LDAP::User do
double(uid: 'my-uid', provider: 'ldapmain', info: double(info))
end
describe :changed? do
it "marks existing ldap user as changed" do
existing_user = create(:omniauth_user, extern_uid: 'my-uid', provider: 'ldapmain')
expect(gl_user.changed?).to be_true
end
it "marks existing non-ldap user if the email matches as changed" do
existing_user = create(:user, email: 'john@example.com')
expect(gl_user.changed?).to be_true
end
it "dont marks existing ldap user as changed" do
existing_user = create(:omniauth_user, email: 'john@example.com', extern_uid: 'my-uid', provider: 'ldapmain')
expect(gl_user.changed?).to be_false
end
end
describe :find_or_create do
it "finds the user if already existing" do
existing_user = create(:omniauth_user, extern_uid: 'my-uid', provider: 'ldapmain')
......
require 'rspec'
require_relative '../../lib/repository_cache'
describe RepositoryCache do
let(:backend) { double('backend').as_null_object }
let(:cache) { RepositoryCache.new('example', backend) }
describe '#cache_key' do
it 'includes the namespace' do
expect(cache.cache_key(:foo)).to eq 'foo:example'
end
end
describe '#expire' do
it 'expires the given key from the cache' do
cache.expire(:foo)
expect(backend).to have_received(:delete).with('foo:example')
end
end
describe '#fetch' do
it 'fetches the given key from the cache' do
cache.fetch(:bar)
expect(backend).to have_received(:fetch).with('bar:example')
end
it 'accepts a block' do
p = -> {}
cache.fetch(:baz, &p)
expect(backend).to have_received(:fetch).with('baz:example', &p)
end
end
end
......@@ -161,8 +161,8 @@ describe Issue, 'Votes' do
add_note '+1 I still like this'
add_note '+1 I really like this'
add_note '+1 Give me this now!!!!'
p issue.downvotes.should == 0
p issue.upvotes.should == 1
issue.downvotes.should == 0
issue.upvotes.should == 1
end
it 'should count a users vote only once without caring about comments' do
......@@ -171,8 +171,8 @@ describe Issue, 'Votes' do
add_note 'Another comment'
add_note '+1 vote'
add_note 'final comment'
p issue.downvotes.should == 0
p issue.upvotes.should == 1
issue.downvotes.should == 0
issue.upvotes.should == 1
end
end
......
......@@ -4,6 +4,7 @@
#
# id :integer not null, primary key
# default_projects_limit :integer
# default_branch_protection :integer
# signup_enabled :boolean
# signin_enabled :boolean
# gravatar_enabled :boolean
......
......@@ -10,7 +10,7 @@ describe Member do
it { should validate_presence_of(:user) }
it { should validate_presence_of(:source) }
it { should ensure_inclusion_of(:access_level).in_array(Gitlab::Access.values) }
it { should validate_inclusion_of(:access_level).in_array(Gitlab::Access.values) }
end
describe "Delegate methods" do
......
# == Schema Information
#
# Table name: services
#
# id :integer not null, primary key
# type :string(255)
# title :string(255)
# project_id :integer not null
# created_at :datetime
# updated_at :datetime
# active :boolean default(FALSE), not null
# properties :text
#
require 'spec_helper'
describe JiraService do
......
......@@ -14,7 +14,7 @@
# merge_requests_enabled :boolean default(TRUE), not null
# wiki_enabled :boolean default(TRUE), not null
# namespace_id :integer
# issues_tracker :string(255) default('gitlab'), not null
# issues_tracker :string(255) default("gitlab"), not null
# issues_tracker_id :string(255)
# snippets_enabled :boolean default(TRUE), not null
# last_activity_at :datetime
......
......@@ -80,6 +80,24 @@ describe API::API, api: true do
response.status.should == 404
end
end
context 'when using group path in URL' do
it 'should return any existing group' do
get api("/groups/#{group1.path}", admin)
response.status.should == 200
json_response['name'] == group2.name
end
it 'should not return a non existing group' do
get api('/groups/unknown', admin)
response.status.should == 404
end
it 'should not return a group not attached to user1' do
get api("/groups/#{group2.path}", user1)
response.status.should == 403
end
end
end
describe "POST /groups" do
......
......@@ -114,6 +114,19 @@ describe API::API, api: true do
end
end
describe 'GET /projects/:id/merge_request/:merge_request_id/changes' do
it 'should return the change information of the merge_request' do
get api("/projects/#{project.id}/merge_request/#{merge_request.id}/changes", user)
expect(response.status).to eq 200
expect(json_response['changes'].size).to eq(merge_request.diffs.size)
end
it 'returns a 404 when merge_request_id not found' do
get api("/projects/#{project.id}/merge_request/999/changes", user)
expect(response.status).to eq(404)
end
end
describe "POST /projects/:id/merge_requests" do
context 'between branches projects' do
it "should return merge_request" do
......
......@@ -106,7 +106,25 @@ describe GitPushService do
it "when pushing a branch for the first time" do
project.should_receive(:execute_hooks)
project.default_branch.should == "master"
project.protected_branches.should_receive(:create).with({ name: "master" })
project.protected_branches.should_receive(:create).with({ name: "master", developers_can_push: false })
service.execute(project, user, @blankrev, 'newrev', 'refs/heads/master')
end
it "when pushing a branch for the first time with default branch protection disabled" do
ApplicationSetting.any_instance.stub(default_branch_protection: 0)
project.should_receive(:execute_hooks)
project.default_branch.should == "master"
project.protected_branches.should_not_receive(:create)
service.execute(project, user, @blankrev, 'newrev', 'refs/heads/master')
end
it "when pushing a branch for the first time with default branch protection set to 'developers can push'" do
ApplicationSetting.any_instance.stub(default_branch_protection: 1)
project.should_receive(:execute_hooks)
project.default_branch.should == "master"
project.protected_branches.should_receive(:create).with({ name: "master", developers_can_push: true })
service.execute(project, user, @blankrev, 'newrev', 'refs/heads/master')
end
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment