Skip to content

Commit c0fd3df

Browse files
authored
Merge branch 'develop' into FixAsyncResultInvalidValue
2 parents a155766 + a027c76 commit c0fd3df

File tree

5 files changed

+54
-14
lines changed

5 files changed

+54
-14
lines changed

src/Renci.SshNet/Common/AuthenticationPromptEventArgs.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ public class AuthenticationPromptEventArgs : AuthenticationEventArgs
1414
/// <param name="instruction">The instruction.</param>
1515
/// <param name="language">The language.</param>
1616
/// <param name="prompts">The information request prompts.</param>
17-
public AuthenticationPromptEventArgs(string username, string instruction, string language, IEnumerable<AuthenticationPrompt> prompts)
17+
public AuthenticationPromptEventArgs(string username, string instruction, string language, IReadOnlyList<AuthenticationPrompt> prompts)
1818
: base(username)
1919
{
2020
Instruction = instruction;
@@ -35,6 +35,6 @@ public AuthenticationPromptEventArgs(string username, string instruction, string
3535
/// <summary>
3636
/// Gets server information request prompts.
3737
/// </summary>
38-
public IEnumerable<AuthenticationPrompt> Prompts { get; }
38+
public IReadOnlyList<AuthenticationPrompt> Prompts { get; }
3939
}
4040
}

src/Renci.SshNet/KeyboardInteractiveAuthenticationMethod.cs

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -125,9 +125,19 @@ private void Session_UserAuthenticationInformationRequestReceived(object sender,
125125

126126
var informationResponse = new InformationResponseMessage();
127127

128-
foreach (var response in from r in eventArgs.Prompts orderby r.Id ascending select r.Response)
128+
foreach (var prompt in eventArgs.Prompts.OrderBy(r => r.Id))
129129
{
130-
informationResponse.Responses.Add(response);
130+
if (prompt.Response is null)
131+
{
132+
throw new SshAuthenticationException(
133+
$"{nameof(AuthenticationPrompt)}.{nameof(prompt.Response)} is null for " +
134+
$"prompt \"{prompt.Request}\". You can set this by subscribing to " +
135+
$"{nameof(KeyboardInteractiveAuthenticationMethod)}.{nameof(AuthenticationPrompt)} " +
136+
$"and inspecting the {nameof(AuthenticationPromptEventArgs.Prompts)} property " +
137+
$"of the event args.");
138+
}
139+
140+
informationResponse.Responses.Add(prompt.Response);
131141
}
132142

133143
// Send information response message

src/Renci.SshNet/Messages/Authentication/InformationRequestMessage.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ internal sealed class InformationRequestMessage : Message
2929
/// <summary>
3030
/// Gets information request prompts.
3131
/// </summary>
32-
public IEnumerable<AuthenticationPrompt> Prompts { get; private set; }
32+
public IReadOnlyList<AuthenticationPrompt> Prompts { get; private set; }
3333

3434
/// <summary>
3535
/// Called when type specific data need to be loaded.

test/Renci.SshNet.IntegrationTests/AuthenticationMethodFactory.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ public PrivateKeyAuthenticationMethod CreateRegularUserPrivateKeyAuthenticationM
6969
return new PrivateKeyAuthenticationMethod(Users.Regular.UserName, new PrivateKeyFile(memoryStream));
7070
}
7171

72-
public PasswordAuthenticationMethod CreateRegulatUserPasswordAuthenticationMethod()
72+
public PasswordAuthenticationMethod CreateRegularUserPasswordAuthenticationMethod()
7373
{
7474
return new PasswordAuthenticationMethod(Users.Regular.UserName, Users.Regular.Password);
7575
}

test/Renci.SshNet.IntegrationTests/AuthenticationTests.cs

Lines changed: 38 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -161,7 +161,7 @@ public void Multifactor_Password_ExceedsPartialSuccessLimit()
161161
.Update()
162162
.Restart();
163163

164-
var connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegulatUserPasswordAuthenticationMethod());
164+
var connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegularUserPasswordAuthenticationMethod());
165165
using (var client = new SftpClient(connectionInfo))
166166
{
167167
try
@@ -187,7 +187,7 @@ public void Multifactor_Password_MatchPartialSuccessLimit()
187187
.Update()
188188
.Restart();
189189

190-
var connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegulatUserPasswordAuthenticationMethod());
190+
var connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegularUserPasswordAuthenticationMethod());
191191
using (var client = new SftpClient(connectionInfo))
192192
{
193193
client.Connect();
@@ -205,7 +205,7 @@ public void Multifactor_Password_Or_PublicKeyAndKeyboardInteractive()
205205
.Restart();
206206

207207
var connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegularUserPrivateKeyAuthenticationMethod(),
208-
_authenticationMethodFactory.CreateRegulatUserPasswordAuthenticationMethod());
208+
_authenticationMethodFactory.CreateRegularUserPasswordAuthenticationMethod());
209209
using (var client = new SftpClient(connectionInfo))
210210
{
211211
client.Connect();
@@ -243,7 +243,7 @@ public void Multifactor_PasswordAndPublicKey_Or_PasswordAndPassword()
243243
.Update()
244244
.Restart();
245245

246-
var connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegulatUserPasswordAuthenticationMethod(),
246+
var connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegularUserPasswordAuthenticationMethod(),
247247
_authenticationMethodFactory.CreateRegularUserPrivateKeyAuthenticationMethodWithBadKey());
248248
using (var client = new SftpClient(connectionInfo))
249249
{
@@ -275,14 +275,14 @@ public void Multifactor_PasswordAndPassword_Or_PublicKey()
275275
.Update()
276276
.Restart();
277277

278-
var connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegulatUserPasswordAuthenticationMethod(),
278+
var connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegularUserPasswordAuthenticationMethod(),
279279
_authenticationMethodFactory.CreateRegularUserPrivateKeyAuthenticationMethodWithBadKey());
280280
using (var client = new SftpClient(connectionInfo))
281281
{
282282
client.Connect();
283283
}
284284

285-
connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegulatUserPasswordAuthenticationMethod());
285+
connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegularUserPasswordAuthenticationMethod());
286286
using (var client = new SftpClient(connectionInfo))
287287
{
288288
client.Connect();
@@ -297,13 +297,13 @@ public void Multifactor_Password_Or_Password()
297297
.Update()
298298
.Restart();
299299

300-
var connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegulatUserPasswordAuthenticationMethod());
300+
var connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegularUserPasswordAuthenticationMethod());
301301
using (var client = new SftpClient(connectionInfo))
302302
{
303303
client.Connect();
304304
}
305305

306-
connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegulatUserPasswordAuthenticationMethod(),
306+
connectionInfo = _connectionInfoFactory.Create(_authenticationMethodFactory.CreateRegularUserPasswordAuthenticationMethod(),
307307
_authenticationMethodFactory.CreateRegularUserPrivateKeyAuthenticationMethodWithBadKey());
308308
using (var client = new SftpClient(connectionInfo))
309309
{
@@ -423,5 +423,35 @@ public void KeyboardInteractiveConnectionInfo()
423423
Assert.AreEqual(connectionInfo.Host, SshServerHostName);
424424
Assert.AreEqual(connectionInfo.Username, User.UserName);
425425
}
426+
427+
[TestMethod]
428+
public void KeyboardInteractive_NoResponseSet_ThrowsSshAuthenticationException()
429+
{
430+
// ...instead of a cryptic ArgumentNullException
431+
// https://github.com/sshnet/SSH.NET/issues/382
432+
433+
_remoteSshdConfig.WithAuthenticationMethods(Users.Regular.UserName, "keyboard-interactive")
434+
.WithChallengeResponseAuthentication(true)
435+
.WithKeyboardInteractiveAuthentication(true)
436+
.WithUsePAM(true)
437+
.Update()
438+
.Restart();
439+
440+
var connectionInfo = _connectionInfoFactory.Create(new KeyboardInteractiveAuthenticationMethod(Users.Regular.UserName));
441+
442+
using (var client = new SftpClient(connectionInfo))
443+
{
444+
try
445+
{
446+
client.Connect();
447+
Assert.Fail();
448+
}
449+
catch (SshAuthenticationException ex)
450+
{
451+
Assert.IsNull(ex.InnerException);
452+
Assert.IsTrue(ex.Message.StartsWith("AuthenticationPrompt.Response is null for prompt \"Password: \""), $"Message was \"{ex.Message}\"");
453+
}
454+
}
455+
}
426456
}
427457
}

0 commit comments

Comments
 (0)